[IMP] *: convert to private methods

render, render_template, load, activity_schedule_with_view,
get_website_pages should all be private:
It should not be possible to render an aribtrary template only with
its name or id

Still need to render some qweb views from js so the method
render_template is kept public.
This explains why the website editor still need read access on
ir.ui.view as we want to allow any snippet to be rendered.
This commit is contained in:
Martin Trigaux
2020-05-14 13:59:10 +02:00
parent 56a8c9e431
commit d9287caf94
88 changed files with 207 additions and 196 deletions
+2 -2
View File
@@ -16,7 +16,7 @@ class OnboardingController(http.Controller):
return {}
return {
'html': request.env.ref('account.account_invoice_onboarding_panel').render({
'html': request.env.ref('account.account_invoice_onboarding_panel')._render({
'company': company,
'state': company.get_and_update_account_invoice_onboarding_state()
})
@@ -34,7 +34,7 @@ class OnboardingController(http.Controller):
return {}
return {
'html': request.env.ref('account.account_dashboard_onboarding_panel').render({
'html': request.env.ref('account.account_dashboard_onboarding_panel')._render({
'company': company,
'state': company.get_and_update_account_dashboard_onboarding_state()
})
@@ -396,7 +396,7 @@ class AccountBankStatement(models.Model):
# Bank statement report.
if statement.journal_id.type == 'bank':
content, content_type = self.env.ref('account.action_report_account_statement').render(statement.id)
content, content_type = self.env.ref('account.action_report_account_statement')._render(statement.id)
self.env['ir.attachment'].create({
'name': statement.name and _("Bank Statement %s.pdf") % statement.name or _("Bank Statement.pdf"),
'type': 'binary',
@@ -43,7 +43,7 @@ class AccountMove(models.Model):
'format_date': format_date,
'format_monetary': format_monetary,
}
content = self.env.ref('account_facturx.account_invoice_facturx_export').render(template_values)
content = self.env.ref('account_facturx.account_invoice_facturx_export')._render(template_values)
return b"<?xml version='1.0' encoding='UTF-8'?>" + content
def _import_facturx_invoice(self, tree):
+1 -1
View File
@@ -76,7 +76,7 @@ class CalendarController(http.Controller):
# - we need a template rendering which is not lazy, to render before cursor closing
# - we need to display the template in the language of the user (not possible with
# request.render())
response_content = request.env['ir.ui.view'].with_context(lang=lang).render_template(
response_content = request.env['ir.ui.view'].with_context(lang=lang)._render_template(
'calendar.invitation_page_anonymous', {
'event': event,
'attendee': attendee,
@@ -91,7 +91,7 @@ class EventRegistration(models.Model):
'new_ticket_name': new_event_ticket.name
}
user_id = registration.event_id.user_id.id or registration.sale_order_id.user_id.id or fallback_user_id
registration.sale_order_id.activity_schedule_with_view(
registration.sale_order_id._activity_schedule_with_view(
'mail.mail_activity_data_warning',
user_id=user_id,
views_or_xmlid='event_sale.event_ticket_id_change_exception',
+2 -2
View File
@@ -25,7 +25,7 @@ class TestMultiCompany(TestHrCommon):
def test_multi_company_report(self):
content, content_type = self.env.ref('hr.hr_employee_print_badge').with_user(self.res_users_hr_officer).with_context(
allowed_company_ids=[self.company_1.id, self.company_2.id]
).render_qweb_pdf(res_ids=self.employees.ids)
)._render_qweb_pdf(res_ids=self.employees.ids)
self.assertIn(b'Bidule', content)
self.assertIn(b'Machin', content)
@@ -33,4 +33,4 @@ class TestMultiCompany(TestHrCommon):
with self.assertRaises(QWebException): # CacheMiss followed by AccessError
content, content_type = self.env.ref('hr.hr_employee_print_badge').with_user(self.res_users_hr_officer).with_company(
self.company_1
).render_qweb_pdf(res_ids=self.employees.ids)
)._render_qweb_pdf(res_ids=self.employees.ids)
+1 -1
View File
@@ -665,7 +665,7 @@ class HrExpense(models.Model):
def _send_expense_success_mail(self, msg_dict, expense):
mail_template_id = 'hr_expense.hr_expense_template_register' if expense.employee_id.user_id else 'hr_expense.hr_expense_template_register_no_user'
expense_template = self.env.ref(mail_template_id)
rendered_body = expense_template.render({'expense': expense}, engine='ir.qweb')
rendered_body = expense_template._render({'expense': expense}, engine='ir.qweb')
body = self.env['mail.render.mixin']._replace_local_links(rendered_body)
# TDE TODO: seems louche, check to use notify
if expense.employee_id.user_id.partner_id:
+2 -2
View File
@@ -601,7 +601,7 @@ class IrHttp(models.AbstractModel):
@classmethod
def _get_error_html(cls, env, code, values):
return code, env['ir.ui.view'].render_template('http_routing.%s' % code, values)
return code, env['ir.ui.view']._render_template('http_routing.%s' % code, values)
@classmethod
def _handle_exception(cls, exception):
@@ -658,6 +658,6 @@ class IrHttp(models.AbstractModel):
try:
code, html = cls._get_error_html(env, code, values)
except Exception:
code, html = 418, env['ir.ui.view'].render_template('http_routing.http_error', values)
code, html = 418, env['ir.ui.view']._render_template('http_routing.http_error', values)
return werkzeug.wrappers.Response(html, status=code, content_type='text/html;charset=utf-8')
+1 -1
View File
@@ -94,7 +94,7 @@ def authorize(env, key, account_token, credit, dbuuid=False, description=None, c
except InsufficientCreditError as e:
if credit_template:
arguments = json.loads(e.args[0])
arguments['body'] = pycompat.to_text(env['ir.qweb'].render(credit_template))
arguments['body'] = pycompat.to_text(env['ir.qweb']._render(credit_template))
e.args = (json.dumps(arguments),)
raise e
return transaction_token
@@ -65,7 +65,7 @@ class ImLivechatChannel(models.Model):
}
for record in self:
values["channel_id"] = record.id
record.script_external = view.render(values)
record.script_external = view._render(values)
def _compute_web_page_link(self):
base_url = self.env['ir.config_parameter'].sudo().get_param('web.base.url')
+1 -1
View File
@@ -184,7 +184,7 @@ class MailChannel(models.Model):
"channel": self,
}
template = self.env.ref('im_livechat.livechat_email_template')
mail_body = template.render(render_context, engine='ir.qweb', minimal_qcontext=True)
mail_body = template._render(render_context, engine='ir.qweb', minimal_qcontext=True)
mail_body = self.env['mail.render.mixin']._replace_local_links(mail_body)
mail = self.env['mail.mail'].sudo().create({
'subject': _('Conversation with %s') % self.livechat_operator_id.name,
+2 -2
View File
@@ -36,10 +36,10 @@ class MailTemplate(models.Model):
isr_report_name = 'ISR-' + inv_print_name + '.pdf'
qr_report_name = 'QR-bill-' + inv_print_name + '.pdf'
isr_pdf = self.env.ref('l10n_ch.l10n_ch_isr_report').render_qweb_pdf(record.ids)[0]
isr_pdf = self.env.ref('l10n_ch.l10n_ch_isr_report')._render_qweb_pdf(record.ids)[0]
isr_pdf = base64.b64encode(isr_pdf)
qr_pdf = self.env.ref('l10n_ch.l10n_ch_qr_report').render_qweb_pdf(record.ids)[0]
qr_pdf = self.env.ref('l10n_ch.l10n_ch_qr_report')._render_qweb_pdf(record.ids)[0]
qr_pdf = base64.b64encode(qr_pdf)
new_attachments = [(isr_report_name, isr_pdf), (qr_report_name, qr_pdf)]
+2 -2
View File
@@ -233,7 +233,7 @@ class AccountMove(models.Model):
else:
document_type = 'TD0X'
pdf = self.env.ref('account.account_invoices').render_qweb_pdf(self.id)[0]
pdf = self.env.ref('account.account_invoices')._render_qweb_pdf(self.id)[0]
pdf = base64.b64encode(pdf)
pdf_name = re.sub(r'\W+', '', self.name) + '.pdf'
@@ -254,7 +254,7 @@ class AccountMove(models.Model):
'pdf': pdf,
'pdf_name': pdf_name,
}
content = self.env.ref('l10n_it_edi.account_invoice_it_FatturaPA_export').render(template_values)
content = self.env.ref('l10n_it_edi.account_invoice_it_FatturaPA_export')._render(template_values)
return content
def send_pec_mail(self):
+1 -1
View File
@@ -60,7 +60,7 @@ class LunchController(http.Controller):
@http.route('/lunch/payment_message', type='json', auth='user')
def payment_message(self):
return {'message': request.env['ir.qweb'].render('lunch.lunch_payment_dialog', {})}
return {'message': request.env['ir.qweb']._render('lunch.lunch_payment_dialog', {})}
@http.route('/lunch/user_location_set', type='json', auth='user')
def set_user_location(self, location_id=None, user_id=None):
+3 -3
View File
@@ -393,7 +393,7 @@ class MailActivity(models.Model):
body_template = body_template.with_context(lang=activity.user_id.lang)
activity = activity.with_context(lang=activity.user_id.lang)
model_description = self.env['ir.model']._get(activity.res_model).display_name
body = body_template.render(
body = body_template._render(
dict(
activity=activity,
model_description=model_description,
@@ -798,7 +798,7 @@ class MailActivityMixin(models.AbstractModel):
activities |= self.env['mail.activity'].create(create_vals)
return activities
def activity_schedule_with_view(self, act_type_xmlid='', date_deadline=None, summary='', views_or_xmlid='', render_context=None, **act_values):
def _activity_schedule_with_view(self, act_type_xmlid='', date_deadline=None, summary='', views_or_xmlid='', render_context=None, **act_values):
""" Helper method: Schedule an activity on each record of the current record set.
This method allow to the same mecanism as `activity_schedule`, but provide
2 additionnal parameters:
@@ -821,7 +821,7 @@ class MailActivityMixin(models.AbstractModel):
activities = self.env['mail.activity']
for record in self:
render_context['object'] = record
note = views.render(render_context, engine='ir.qweb', minimal_qcontext=True)
note = views._render(render_context, engine='ir.qweb', minimal_qcontext=True)
activities |= record.activity_schedule(act_type_xmlid=act_type_xmlid, date_deadline=date_deadline, summary=summary, note=note, **act_values)
return activities
+1 -1
View File
@@ -182,7 +182,7 @@ Only allowed people can contact us at this address.""" % message_dict.get('to'))
else:
body = self._get_alias_bounced_body_fallback(message_dict)
template = self.env.ref('mail.mail_bounce_alias_security', raise_if_not_found=True)
return template.render({
return template._render({
'body': body,
'message': message_dict
}, engine='ir.qweb', minimal_qcontext=True)
+1 -1
View File
@@ -426,7 +426,7 @@ class Channel(models.Model):
create_values = {
'email_from': company.catchall_formatted or company.email_formatted,
'author_id': self.env.user.partner_id.id,
'body_html': view.render({'channel': self, 'partner': partner}, engine='ir.qweb', minimal_qcontext=True),
'body_html': view._render({'channel': self, 'partner': partner}, engine='ir.qweb', minimal_qcontext=True),
'subject': _("Guidelines of channel %s") % self.name,
'recipient_ids': [(4, partner.id)]
}
+1 -1
View File
@@ -935,7 +935,7 @@ class Message(models.Model):
MailThread.message_notify(
partner_ids=moderator.partner_id.ids,
subject=_('Message are pending moderation'), # tocheck: target language
body=template.render({'record': moderator.partner_id}, engine='ir.qweb', minimal_qcontext=True),
body=template._render({'record': moderator.partner_id}, engine='ir.qweb', minimal_qcontext=True),
email_from=moderator.company_id.catchall_formatted or moderator.company_id.email_formatted,
)
+3 -3
View File
@@ -196,9 +196,9 @@ class MailTemplate(models.Model):
report_service = report.report_name
if report.report_type in ['qweb-html', 'qweb-pdf']:
result, format = report.render_qweb_pdf([res_id])
result, format = report._render_qweb_pdf([res_id])
else:
res = report.render([res_id])
res = report._render([res_id])
if not res:
raise UserError(_('Unsupported report type %s found.') % report.report_type)
result, format = res
@@ -267,7 +267,7 @@ class MailTemplate(models.Model):
'company': 'company_id' in record and record['company_id'] or self.env.company,
'record': record,
}
body = template.render(template_ctx, engine='ir.qweb', minimal_qcontext=True)
body = template._render(template_ctx, engine='ir.qweb', minimal_qcontext=True)
values['body_html'] = self.env['mail.render.mixin']._replace_local_links(body)
mail = self.env['mail.mail'].sudo().create(values)
+4 -4
View File
@@ -1015,7 +1015,7 @@ class MailThread(models.AbstractModel):
# check it does not directly contact catchall
if catchall_alias and all(email_localpart == catchall_alias for email_localpart in email_to_localparts):
_logger.info('Routing mail from %s to %s with Message-Id %s: direct write to catchall, bounce', email_from, email_to, message_id)
body = self.env.ref('mail.mail_bounce_catchall').render({
body = self.env.ref('mail.mail_bounce_catchall')._render({
'message': message,
}, engine='ir.qweb')
self._routing_create_bounce_email(email_from, body, message, references=message_id, reply_to=self.env.company.email)
@@ -1968,7 +1968,7 @@ class MailThread(models.AbstractModel):
return
for record in self:
values['object'] = record
rendered_template = views.render(values, engine='ir.qweb', minimal_qcontext=True)
rendered_template = views._render(values, engine='ir.qweb', minimal_qcontext=True)
kwargs['body'] = rendered_template
record.message_post_with_template(False, **kwargs)
@@ -2294,7 +2294,7 @@ class MailThread(models.AbstractModel):
# {actions, button_access, has_button_access, recipients}
if base_template:
mail_body = base_template.render(render_values, engine='ir.qweb', minimal_qcontext=True)
mail_body = base_template._render(render_values, engine='ir.qweb', minimal_qcontext=True)
else:
mail_body = message.body
mail_body = self.env['mail.render.mixin']._replace_local_links(mail_body)
@@ -2886,7 +2886,7 @@ class MailThread(models.AbstractModel):
'model_description': model_description,
'access_link': self._notify_get_action_link('view'),
}
assignation_msg = view.render(values, engine='ir.qweb', minimal_qcontext=True)
assignation_msg = view._render(values, engine='ir.qweb', minimal_qcontext=True)
assignation_msg = self.env['mail.render.mixin']._replace_local_links(assignation_msg)
record.message_notify(
subject=_('You have been assigned to %s') % record.display_name,
@@ -77,7 +77,7 @@ class MailComposeMessage(models.TransientModel):
'email': mail_to,
}
if mail_values.get('body_html') and mass_mail_layout:
mail_values['body_html'] = mass_mail_layout.render({'body': mail_values['body_html']}, engine='ir.qweb', minimal_qcontext=True)
mail_values['body_html'] = mass_mail_layout._render({'body': mail_values['body_html']}, engine='ir.qweb', minimal_qcontext=True)
# propagate ignored state to trace when still-born
if mail_values.get('state') == 'cancel':
trace_vals['ignored'] = fields.Datetime.now()
@@ -31,7 +31,7 @@ class TestMassMailing(models.TransientModel):
'reply_to': mailing.reply_to,
'email_to': test_mail,
'subject': mailing.subject,
'body_html': mass_mail_layout.render({'body': body}, engine='ir.qweb', minimal_qcontext=True),
'body_html': mass_mail_layout._render({'body': body}, engine='ir.qweb', minimal_qcontext=True),
'notification': True,
'mailing_id': mailing.id,
'attachment_ids': [(4, attachment.id) for attachment in mailing.attachment_ids],
+2 -2
View File
@@ -1190,7 +1190,7 @@ class MrpProduction(models.Model):
'impacted_pickings': False,
'cancel': cancel
}
return self.env.ref('mrp.exception_on_mo').render(values=values)
return self.env.ref('mrp.exception_on_mo')._render(values=values)
documents = self.env['stock.picking']._log_activity_get_documents(moves_modification, 'move_dest_ids', 'DOWN', _keys_in_sorted, _keys_in_groupby)
documents = self.env['stock.picking']._less_quantities_than_expected_add_documents(moves_modification, documents)
@@ -1216,7 +1216,7 @@ class MrpProduction(models.Model):
'impacted_object': impacted_object,
'cancel': cancel
}
return self.env.ref('mrp.exception_on_mo').render(values=values)
return self.env.ref('mrp.exception_on_mo')._render(values=values)
self.env['stock.picking']._log_activity(_render_note_exception_quantity_mo, documents)
@@ -44,13 +44,13 @@ class ReportBomStructure(models.AbstractModel):
res['lines']['report_type'] = 'html'
res['lines']['report_structure'] = 'all'
res['lines']['has_attachments'] = res['lines']['attachments'] or any(component['attachments'] for component in res['lines']['components'])
res['lines'] = self.env.ref('mrp.report_mrp_bom').render({'data': res['lines']})
res['lines'] = self.env.ref('mrp.report_mrp_bom')._render({'data': res['lines']})
return res
@api.model
def get_bom(self, bom_id=False, product_id=False, line_qty=False, line_id=False, level=False):
lines = self._get_bom(bom_id=bom_id, product_id=product_id, line_qty=line_qty, line_id=line_id, level=level)
return self.env.ref('mrp.report_mrp_bom_line').render({'data': lines})
return self.env.ref('mrp.report_mrp_bom_line')._render({'data': lines})
@api.model
def get_operations(self, bom_id=False, qty=0, level=0):
@@ -61,7 +61,7 @@ class ReportBomStructure(models.AbstractModel):
'currency': self.env.company.currency_id,
'operations': lines,
}
return self.env.ref('mrp.report_mrp_operation_line').render({'data': values})
return self.env.ref('mrp.report_mrp_operation_line')._render({'data': values})
@api.model
def _get_report_data(self, bom_id, searchQty=0, searchVariant=False):
+1 -1
View File
@@ -478,7 +478,7 @@ class PaymentAcquirer(models.Model):
})
_logger.info('payment.acquirer.render: <%s> values rendered for form payment:\n%s', self.provider, pprint.pformat(values))
return self.view_template_id.render(values, engine='ir.qweb')
return self.view_template_id._render(values, engine='ir.qweb')
def get_s2s_form_xml_id(self):
if self.registration_view_template_id:
+1 -1
View File
@@ -194,7 +194,7 @@ class TxPaypal(models.Model):
if not self.acquirer_id.paypal_pdt_token and not self.acquirer_id.paypal_seller_account and status in ['Completed', 'Processed', 'Pending']:
template = self.env.ref('payment_paypal.mail_template_paypal_invite_user_to_configure', False)
if template:
render_template = template.render({
render_template = template._render({
'acquirer': self.acquirer_id,
}, engine='ir.qweb')
mail_body = self.env['mail.render.mixin']._replace_local_links(render_template)
+1 -1
View File
@@ -61,6 +61,6 @@ class PosController(http.Controller):
@http.route('/pos/sale_details_report', type='http', auth='user')
def print_sale_details(self, date_start=False, date_stop=False, **kw):
r = request.env['report.point_of_sale.report_saledetails']
pdf, _ = request.env.ref('point_of_sale.sale_details_report').with_context(date_start=date_start, date_stop=date_stop).render_qweb_pdf(r)
pdf, _ = request.env.ref('point_of_sale.sale_details_report').with_context(date_start=date_start, date_stop=date_stop)._render_qweb_pdf(r)
pdfhttpheaders = [('Content-Type', 'application/pdf'), ('Content-Length', len(pdf))]
return request.make_response(pdf, headers=pdfhttpheaders)
+1 -1
View File
@@ -99,7 +99,7 @@ class PosConfig(models.Model):
def _compute_customer_html(self):
for config in self:
config.customer_facing_display_html = self.env['ir.qweb'].render('point_of_sale.customer_facing_display_html')
config.customer_facing_display_html = self.env['ir.qweb']._render('point_of_sale.customer_facing_display_html')
name = fields.Char(string='Point of Sale', index=True, required=True, help="An internal identification of the point of sale.")
is_installed_account_accountant = fields.Boolean(string="Is the Full Accounting Installed",
+1 -1
View File
@@ -542,7 +542,7 @@ class PosOrder(models.Model):
}
if self.mapped('account_move'):
report = self.env.ref('point_of_sale.pos_invoice_report').render_qweb_pdf(self.ids[0])
report = self.env.ref('point_of_sale.pos_invoice_report')._render_qweb_pdf(self.ids[0])
filename = name + '.pdf'
attachment = self.env['ir.attachment'].create({
'name': filename,
+1 -1
View File
@@ -371,7 +371,7 @@ class CustomerPortal(Controller):
if not isinstance(report_sudo, type(request.env['ir.actions.report'])):
raise UserError(_("%s is not the reference of a report") % report_ref)
method_name = 'render_qweb_%s' % (report_type)
method_name = '_render_qweb_%s' % (report_type)
report = getattr(report_sudo, method_name)([model.id], data={'report_type': report_type})[0]
reporthttpheaders = [
('Content-Type', 'application/pdf' if report_type == 'pdf' else 'text/html'),
@@ -46,7 +46,7 @@ class MercuryTransaction(models.Model):
data['memo'] = "Odoo " + service.common.exp_version()['server_version']
def _do_request(self, template, data):
xml_transaction = self.env.ref(template).render(data).decode()
xml_transaction = self.env.ref(template)._render(data).decode()
if not data['merchant_id'] or not data['merchant_pwd']:
return "not setup"
@@ -22,7 +22,7 @@ class report_product_pricelist(models.AbstractModel):
self.env.context.get('pricelist_id'),
self.env.context.get('quantities') or [1]
)
return self.env.ref('product.report_pricelist_page').render(render_values)
return self.env.ref('product.report_pricelist_page')._render(render_values)
def _get_report_data(self, active_model, active_ids, pricelist_id, quantities, report_type='html'):
products = []
+1 -1
View File
@@ -185,7 +185,7 @@ class PurchaseOrder(models.Model):
'order_exceptions': order_exceptions.values(),
'impacted_pickings': impacted_pickings,
}
return self.env.ref('purchase_stock.exception_on_po').render(values=values)
return self.env.ref('purchase_stock.exception_on_po')._render(values=values)
documents = self.env['stock.picking']._log_activity_get_documents(purchase_order_lines_quantities, 'move_ids', 'DOWN', _keys_in_sorted, _keys_in_groupby)
filtered_documents = {}
+2 -2
View File
@@ -45,7 +45,7 @@ class Rating(http.Controller):
}
rating.write({'rating': rate, 'consumed': True})
lang = rating.partner_id.lang or get_lang(request.env).code
return request.env['ir.ui.view'].with_context(lang=lang).render_template('rating.rating_external_page_submit', {
return request.env['ir.ui.view'].with_context(lang=lang)._render_template('rating.rating_external_page_submit', {
'rating': rating, 'token': token,
'rate_names': rate_names, 'rate': rate
})
@@ -60,7 +60,7 @@ class Rating(http.Controller):
record_sudo = request.env[rating.res_model].sudo().browse(rating.res_id)
record_sudo.rating_apply(rate, token=token, feedback=kwargs.get('feedback'))
lang = rating.partner_id.lang or get_lang(request.env).code
return request.env['ir.ui.view'].with_context(lang=lang).render_template('rating.rating_external_page_view', {
return request.env['ir.ui.view'].with_context(lang=lang)._render_template('rating.rating_external_page_view', {
'web_base_url': request.env['ir.config_parameter'].sudo().get_param('web.base.url'),
'rating': rating,
})
+1 -1
View File
@@ -19,7 +19,7 @@ class OnboardingController(http.Controller):
return {}
return {
'html': request.env.ref('sale.sale_quotation_onboarding_panel').render({
'html': request.env.ref('sale.sale_quotation_onboarding_panel')._render({
'company': company,
'state': company.get_and_update_sale_quotation_onboarding_state()
})
+1 -1
View File
@@ -231,7 +231,7 @@ class CustomerPortal(CustomerPortal):
order_sudo.action_confirm()
order_sudo._send_order_confirmation_mail()
pdf = request.env.ref('sale.action_report_saleorder').sudo().render_qweb_pdf([order_sudo.id])[0]
pdf = request.env.ref('sale.action_report_saleorder').sudo()._render_qweb_pdf([order_sudo.id])[0]
_message_post_helper(
'sale.order', order_sudo.id, _('Order signed by %s') % (name,),
+3 -3
View File
@@ -28,7 +28,7 @@ class CustomerPortal(CustomerPortal):
'order_line_price_subtotal': format_price(order_line.price_subtotal)
})
try:
results['order_totals_table'] = request.env['ir.ui.view'].render_template('sale.sale_order_portal_content_totals_table', {'sale_order': order_sudo})
results['order_totals_table'] = request.env['ir.ui.view']._render_template('sale.sale_order_portal_content_totals_table', {'sale_order': order_sudo})
except ValueError:
pass
@@ -58,7 +58,7 @@ class CustomerPortal(CustomerPortal):
results = self._get_portal_order_details(order_sudo)
results.update({
'unlink': True,
'sale_template': request.env['ir.ui.view'].render_template('sale.sale_order_portal_content', {
'sale_template': request.env['ir.ui.view']._render_template('sale.sale_order_portal_content', {
'sale_order': order_sudo,
'report_type': "html"
}),
@@ -84,7 +84,7 @@ class CustomerPortal(CustomerPortal):
option_sudo.add_option_to_order()
results = self._get_portal_order_details(order_sudo)
results['sale_template'] = request.env['ir.ui.view'].render_template("sale.sale_order_portal_content", {
results['sale_template'] = request.env['ir.ui.view']._render_template("sale.sale_order_portal_content", {
'sale_order': option_sudo.order_id,
'report_type': "html"
})
@@ -21,7 +21,7 @@ class ProductConfiguratorController(http.Controller):
if pricelist:
product_template = product_template.with_context(pricelist=pricelist.id, partner=request.env.user.partner_id)
return request.env['ir.ui.view'].render_template("sale_product_configurator.configure", {
return request.env['ir.ui.view']._render_template("sale_product_configurator.configure", {
'product': product_template,
'pricelist': pricelist,
'add_qty': add_qty,
@@ -48,7 +48,7 @@ class ProductConfiguratorController(http.Controller):
# They are kept in the context since they are not linked to this product variant
parent_combination |= product.env.context.get('no_variant_attribute_values')
return request.env['ir.ui.view'].render_template("sale_product_configurator.optional_product_items", {
return request.env['ir.ui.view']._render_template("sale_product_configurator.optional_product_items", {
'product': product,
'parent_name': product.name,
'parent_combination': parent_combination,
@@ -72,7 +72,7 @@ class ProductConfiguratorController(http.Controller):
if no_variant_attribute_values:
product = product.with_context(no_variant_attribute_values=no_variant_attribute_values)
return request.env['ir.ui.view'].render_template("sale_product_configurator.optional_products_modal", {
return request.env['ir.ui.view']._render_template("sale_product_configurator.optional_products_modal", {
'product': product,
'combination': combination,
'add_qty': add_qty,
@@ -58,7 +58,7 @@ class PurchaseOrder(models.Model):
sale_to_notify_map[sale_order] |= purchase_line
for sale_order, purchase_order_lines in sale_to_notify_map.items():
sale_order.activity_schedule_with_view('mail.mail_activity_data_warning',
sale_order._activity_schedule_with_view('mail.mail_activity_data_warning',
user_id=sale_order.user_id.id or self.env.uid,
views_or_xmlid='sale_purchase.exception_sale_on_purchase_cancellation',
render_context={
+2 -2
View File
@@ -70,7 +70,7 @@ class SaleOrder(models.Model):
purchase_to_notify_map[purchase_line.order_id] |= purchase_line.sale_line_id
for purchase_order, sale_order_lines in purchase_to_notify_map.items():
purchase_order.activity_schedule_with_view('mail.mail_activity_data_warning',
purchase_order._activity_schedule_with_view('mail.mail_activity_data_warning',
user_id=purchase_order.user_id.id or self.env.uid,
views_or_xmlid='sale_purchase.exception_purchase_on_sale_cancellation',
render_context={
@@ -161,7 +161,7 @@ class SaleOrderLine(models.Model):
'sale_orders': sale_lines.mapped('order_id'),
'origin_values': origin_values,
}
purchase_order.activity_schedule_with_view('mail.mail_activity_data_warning',
purchase_order._activity_schedule_with_view('mail.mail_activity_data_warning',
user_id=purchase_order.user_id.id or self.env.uid,
views_or_xmlid='sale_purchase.exception_purchase_on_sale_quantity_decreased',
render_context=render_context)
+1 -1
View File
@@ -30,7 +30,7 @@ class SaleStockPortal(CustomerPortal):
return request.redirect('/my')
# print report as sudo, since it require access to product, taxes, payment term etc.. and portal does not have those access rights.
pdf = request.env.ref('stock.action_report_delivery').sudo().render_qweb_pdf([picking_sudo.id])[0]
pdf = request.env.ref('stock.action_report_delivery').sudo()._render_qweb_pdf([picking_sudo.id])[0]
pdfhttpheaders = [
('Content-Type', 'application/pdf'),
('Content-Length', len(pdf)),
+1 -1
View File
@@ -239,7 +239,7 @@ class SaleOrder(models.Model):
'impacted_pickings': impacted_pickings,
'cancel': cancel
}
return self.env.ref('sale_stock.exception_on_so').render(values=values)
return self.env.ref('sale_stock.exception_on_so')._render(values=values)
self.env['stock.picking']._log_activity(_render_note_exception_quantity_so, documents)
+1 -1
View File
@@ -104,7 +104,7 @@ class StockPicking(models.Model):
'origin_picking': origin_picking,
'moves_information': moves_information.values(),
}
return self.env.ref('sale_stock.exception_on_picking').render(values=values)
return self.env.ref('sale_stock.exception_on_picking')._render(values=values)
documents = self._log_activity_get_documents(moves, 'sale_line_id', 'DOWN', _keys_in_sorted, _keys_in_groupby)
self._log_activity(_render_note_exception_quantity, documents)
+1 -1
View File
@@ -130,7 +130,7 @@ class SnailmailLetter(models.Model):
else:
report_name = 'Document'
filename = "%s.%s" % (report_name, "pdf")
pdf_bin, _ = report.with_context(snailmail_layout=not self.cover).render_qweb_pdf(self.res_id)
pdf_bin, _ = report.with_context(snailmail_layout=not self.cover)._render_qweb_pdf(self.res_id)
attachment = self.env['ir.attachment'].create({
'name': filename,
'datas': base64.b64encode(pdf_bin),
+2 -2
View File
@@ -1163,7 +1163,7 @@ class Picking(models.Model):
'moves_information': rendering_context.values(),
'impacted_pickings': impacted_pickings,
}
return self.env.ref('stock.exception_on_picking').render(values=values)
return self.env.ref('stock.exception_on_picking')._render(values=values)
documents = self._log_activity_get_documents(moves, 'move_dest_ids', 'DOWN', _keys_in_sorted, _keys_in_groupby)
documents = self._less_quantities_than_expected_add_documents(moves, documents)
@@ -1329,7 +1329,7 @@ class Picking(models.Model):
def _attach_sign(self):
""" Render the delivery report in pdf and attach it to the picking in `self`. """
self.ensure_one()
report = self.env.ref('stock.action_report_delivery').render_qweb_pdf(self.id)
report = self.env.ref('stock.action_report_delivery')._render_qweb_pdf(self.id)
filename = "%s_signed_delivery_slip" % self.name
if self.partner_id:
message = _('Order signed by %s') % (self.partner_id.name)
+4 -4
View File
@@ -212,13 +212,13 @@ class MrpStockReport(models.TransientModel):
if not config['test_enable']:
context['commit_assetsbundle'] = True
body = self.env['ir.ui.view'].with_context(context).render_template(
body = self.env['ir.ui.view'].with_context(context)._render_template(
"stock.report_stock_inventory_print",
values=dict(rcontext, lines=lines, report=self, context=self),
)
header = self.env['ir.actions.report'].render_template("web.internal_layout", values=rcontext)
header = self.env['ir.actions.report'].render_template("web.minimal_layout", values=dict(rcontext, subst=True, body=header))
header = self.env['ir.actions.report']._render_template("web.internal_layout", values=rcontext)
header = self.env['ir.actions.report']._render_template("web.minimal_layout", values=dict(rcontext, subst=True, body=header))
return self.env['ir.actions.report']._run_wkhtmltopdf(
[body],
@@ -232,7 +232,7 @@ class MrpStockReport(models.TransientModel):
rcontext = {}
context = dict(self.env.context)
rcontext['lines'] = self.with_context(context).get_lines()
result['html'] = self.env.ref('stock.report_stock_inventory').render(rcontext)
result['html'] = self.env.ref('stock.report_stock_inventory')._render(rcontext)
return result
@api.model
+1 -1
View File
@@ -24,7 +24,7 @@ class TestReports(TransactionCase):
report = self.env.ref('stock.label_lot_template')
target = b'\n\n\n^XA\n^FO100,50\n^A0N,44,33^FD[C418]Mellohi^FS\n^FO100,100\n^A0N,44,33^FDLN/SN:Volume-Beta^FS\n^FO100,150^BY3\n^BCN,100,Y,N,N\n^FDVolume-Beta^FS\n^XZ\n\n\n'
rendering, qweb_type = report.render_qweb_text(lot1.id)
rendering, qweb_type = report._render_qweb_text(lot1.id)
self.assertEqual(target, rendering.replace(b' ', b''), 'The rendering is not good')
self.assertEqual(qweb_type, 'text', 'the report type is not good')
+6 -6
View File
@@ -318,22 +318,22 @@ class Survey(http.Controller):
survey_content = False
if answer_sudo.state == 'done':
survey_content = request.env.ref('survey.survey_fill_form_done').render(survey_data)
survey_content = request.env.ref('survey.survey_fill_form_done')._render(survey_data)
else:
survey_content = request.env.ref('survey.survey_fill_form_in_progress').render(survey_data)
survey_content = request.env.ref('survey.survey_fill_form_in_progress')._render(survey_data)
survey_progress = False
if answer_sudo.state == 'in_progress' and not survey_data.get('question', request.env['survey.question']).is_page:
if survey_sudo.questions_layout == 'page_per_section':
page_ids = survey_sudo.page_ids.ids
survey_progress = request.env.ref('survey.survey_progression').render({
survey_progress = request.env.ref('survey.survey_progression')._render({
'survey': survey_sudo,
'page_ids': page_ids,
'page_number': page_ids.index(survey_data['page'].id) + (1 if survey_sudo.progression_mode == 'number' else 0)
})
elif survey_sudo.questions_layout == 'page_per_question':
page_ids = survey_sudo.question_ids.ids
survey_progress = request.env.ref('survey.survey_progression').render({
survey_progress = request.env.ref('survey.survey_progression')._render({
'survey': survey_sudo,
'page_ids': page_ids,
'page_number': page_ids.index(survey_data['question'].id)
@@ -342,7 +342,7 @@ class Survey(http.Controller):
return {
'survey_content': survey_content,
'survey_progress': survey_progress,
'survey_navigation': request.env.ref('survey.survey_navigation').render(survey_data),
'survey_navigation': request.env.ref('survey.survey_navigation')._render(survey_data),
}
@http.route('/survey/<string:survey_token>/<string:answer_token>', type='http', auth='public', website=True)
@@ -629,7 +629,7 @@ class Survey(http.Controller):
return request.render('survey.survey_page_statistics', template_values)
def _generate_report(self, user_input, download=True):
report = request.env.ref('survey.certification_report').sudo().render_qweb_pdf([user_input.id], data={'report_type': 'pdf'})[0]
report = request.env.ref('survey.certification_report').sudo()._render_qweb_pdf([user_input.id], data={'report_type': 'pdf'})[0]
report_content_disposition = content_disposition('Certification.pdf')
if not download:
@@ -108,7 +108,7 @@ class UserInputSession(http.Controller):
template_values = self._prepare_manage_session_values(survey)
template_values['is_rpc_call'] = True
return request.env.ref('survey.user_input_session_manage_content').render(template_values)
return request.env.ref('survey.user_input_session_manage_content')._render(template_values)
else:
return False
@@ -146,7 +146,7 @@ class UserInputSession(http.Controller):
# no open session
return ''
return request.env.ref('survey.user_input_session_leaderboard').render({
return request.env.ref('survey.user_input_session_leaderboard')._render({
'animate_width': True,
'leaderboard': survey._prepare_leaderboard_values()
})
+1 -1
View File
@@ -234,7 +234,7 @@ class SurveyInvite(models.TransientModel):
'model_description': self.env['ir.model']._get('survey.survey').display_name,
'company': self.env.company,
}
body = template.render(template_ctx, engine='ir.qweb', minimal_qcontext=True)
body = template._render(template_ctx, engine='ir.qweb', minimal_qcontext=True)
mail_values['body_html'] = self.env['mail.render.mixin']._replace_local_links(body)
return self.env['mail.mail'].sudo().create(mail_values)
+3 -3
View File
@@ -1974,14 +1974,14 @@ class ReportController(http.Controller):
del data['context']['lang']
context.update(data['context'])
if converter == 'html':
html = report.with_context(context).render_qweb_html(docids, data=data)[0]
html = report.with_context(context)._render_qweb_html(docids, data=data)[0]
return request.make_response(html)
elif converter == 'pdf':
pdf = report.with_context(context).render_qweb_pdf(docids, data=data)[0]
pdf = report.with_context(context)._render_qweb_pdf(docids, data=data)[0]
pdfhttpheaders = [('Content-Type', 'application/pdf'), ('Content-Length', len(pdf))]
return request.make_response(pdf, headers=pdfhttpheaders)
elif converter == 'text':
text = report.with_context(context).render_qweb_text(docids, data=data)[0]
text = report.with_context(context)._render_qweb_text(docids, data=data)[0]
texthttpheaders = [('Content-Type', 'text/plain'), ('Content-Length', len(text))]
return request.make_response(text, headers=texthttpheaders)
else:
+2 -2
View File
@@ -192,7 +192,7 @@ class Base(models.AbstractModel):
@api.model
def qweb_render_view(self, view_id, domain):
assert view_id
return self.env['ir.qweb'].render(
return self.env['ir.qweb']._render(
view_id, {
**self.env['ir.ui.view']._prepare_qcontext(),
**self._qweb_prepare_qcontext(view_id, domain),
@@ -526,7 +526,7 @@ class ResCompany(models.Model):
# One bundle for everyone, so this method
# necessarily updates the style for every company at once
company_ids = self.sudo().search([])
company_styles = template_style.render({
company_styles = template_style._render({
'company_ids': company_ids,
})
return base64.b64encode((company_styles))
+1 -1
View File
@@ -456,7 +456,7 @@ var loadAsset = (function () {
if (tplRoute === '/web/dataset/call_kw/') {
Object.assign(params, {
model: 'ir.ui.view',
method: 'render_template',
method: 'render_public_asset',
});
}
cache[xmlId] = rpc(tplRoute, params).then(function (xml) {
+1 -1
View File
@@ -476,4 +476,4 @@ class Web_Editor(http.Controller):
if request.env.user._is_public() \
and xmlid in request.env['web_editor.assets']._get_public_asset_xmlids():
View = View.sudo()
return View.render_template(xmlid, {k: values[k] for k in values if k in trusted_value_keys})
return View._render_template(xmlid, {k: values[k] for k in values if k in trusted_value_keys})
+2 -2
View File
@@ -15,7 +15,7 @@ _logger = logging.getLogger(__name__)
class IrUiView(models.Model):
_inherit = 'ir.ui.view'
def render(self, values=None, engine='ir.qweb', minimal_qcontext=False):
def _render(self, values=None, engine='ir.qweb', minimal_qcontext=False):
if values and values.get('editable'):
try:
self.check_access_rights('write')
@@ -23,7 +23,7 @@ class IrUiView(models.Model):
except AccessError:
values['editable'] = False
return super(IrUiView, self).render(values=values, engine=engine, minimal_qcontext=minimal_qcontext)
return super(IrUiView, self)._render(values=values, engine=engine, minimal_qcontext=minimal_qcontext)
#------------------------------------------------------
# Save from html
@@ -1034,7 +1034,7 @@ var SnippetsMenu = Widget.extend({
}
this._defLoadSnippets = this._rpc({
model: 'ir.ui.view',
method: 'render_template',
method: 'render_public_asset',
args: [this.options.snippets, {}],
kwargs: {
context: this.options.context,
+1 -1
View File
@@ -98,7 +98,7 @@ MockServer.include({
if (args.method === 'read_template' && args.args[0] === "web_editor.colorpicker") {
return COLOR_PICKER_TEMPLATE;
}
if (args.method === 'render_template' && args.args[0] === "web_editor.snippets") {
if (args.method === 'render_public_asset' && args.args[0] === "web_editor.snippets") {
return SNIPPETS_TEMPLATE;
}
}
+2 -2
View File
@@ -129,7 +129,7 @@ class TestConvertBack(common.TransactionCase):
field_value = 'record.%s' % field
e.set('t-field', field_value)
rendered = self.env['ir.qweb'].render(t, {'record': record})
rendered = self.env['ir.qweb']._render(t, {'record': record})
element = html.fromstring(rendered, parser=html.HTMLParser(encoding='utf-8'))
model = 'ir.qweb.field.' + element.get('data-oe-type', '')
@@ -197,7 +197,7 @@ class TestConvertBack(common.TransactionCase):
field_value = 'record.%s' % field
e.set('t-field', field_value)
rendered = self.env['ir.qweb'].render(t, {'record': record})
rendered = self.env['ir.qweb']._render(t, {'record': record})
element = html.fromstring(rendered, parser=html.HTMLParser(encoding='utf-8'))
# emulate edition
+6 -6
View File
@@ -167,15 +167,15 @@ class Website(Home):
sitemaps.unlink()
pages = 0
locs = request.website.with_user(request.website.user_id).enumerate_pages()
locs = request.website.with_user(request.website.user_id)._enumerate_pages()
while True:
values = {
'locs': islice(locs, 0, LOC_PER_SITEMAP),
'url_root': request.httprequest.url_root[:-1],
}
urls = View.render_template('website.sitemap_locs', values)
urls = View._render_template('website.sitemap_locs', values)
if urls.strip():
content = View.render_template('website.sitemap_xml', {'content': urls})
content = View._render_template('website.sitemap_xml', {'content': urls})
pages += 1
last_sitemap = create_sitemap('/sitemap-%d-%d.xml' % (current_website.id, pages), content)
else:
@@ -194,7 +194,7 @@ class Website(Home):
pages_with_website = ["%d-%d" % (current_website.id, p) for p in range(1, pages + 1)]
# Sitemaps must be split in several smaller files with a sitemap index
content = View.render_template('website.sitemap_index_xml', {
content = View._render_template('website.sitemap_index_xml', {
'pages': pages_with_website,
'url_root': request.httprequest.url_root,
})
@@ -238,7 +238,7 @@ class Website(Home):
matching_urls = set(map(lambda match: match['value'], matching_pages))
matching_last_modified = []
last_modified_pages = current_website.get_website_pages(order='write_date desc', limit=5)
last_modified_pages = current_website._get_website_pages(order='write_date desc', limit=5)
for url, name in last_modified_pages.mapped(lambda p: (p.url, p.name)):
if needle.lower() in name.lower() or needle.lower() in url.lower() and url not in matching_urls:
matching_last_modified.append({
@@ -474,7 +474,7 @@ class Website(Home):
View = request.env['ir.ui.view']
res = {}
for id_or_xml_id in ids_or_xml_ids:
res[id_or_xml_id] = View.render_template(id_or_xml_id, values)
res[id_or_xml_id] = View._render_template(id_or_xml_id, values)
return res
@http.route(['/website/update_visitor_timezone'], type='json', auth="public", website=True)
+1 -1
View File
@@ -323,7 +323,7 @@ class Http(models.AbstractModel):
@classmethod
def _get_error_html(cls, env, code, values):
if code in ('page_404', 'protected_403'):
return code.split('_')[1], env['ir.ui.view'].render_template('website.%s' % code, values)
return code.split('_')[1], env['ir.ui.view']._render_template('website.%s' % code, values)
return super(Http, cls)._get_error_html(env, code, values)
def binary_content(self, xmlid=None, model='ir.attachment', id=None, field='datas',
+2 -2
View File
@@ -384,7 +384,7 @@ class View(models.Model):
return False
return True
def render(self, values=None, engine='ir.qweb', minimal_qcontext=False):
def _render(self, values=None, engine='ir.qweb', minimal_qcontext=False):
""" Render the template. If website is enabled on request, then extend rendering context with website values. """
self._handle_visibility(do_raise=True)
new_context = dict(self._context)
@@ -411,7 +411,7 @@ class View(models.Model):
if self._context != new_context:
self = self.with_context(new_context)
return super(View, self).render(values, engine=engine, minimal_qcontext=minimal_qcontext)
return super(View, self)._render(values, engine=engine, minimal_qcontext=minimal_qcontext)
@api.model
def _prepare_qcontext(self):
+4 -4
View File
@@ -760,7 +760,7 @@ class Website(models.Model):
return all(p.name in rule._converters for p in params
if p.kind in supported_kinds and has_no_default(p))
def enumerate_pages(self, query_string=None, force=False):
def _enumerate_pages(self, query_string=None, force=False):
""" Available pages in the website/CMS. This is mostly used for links
generation and can be overridden by modules setting up new HTML
controllers for dynamic pages (e.g. blog).
@@ -850,7 +850,7 @@ class Website(models.Model):
if query_string:
domain += [('url', 'like', query_string)]
pages = self.get_website_pages(domain)
pages = self._get_website_pages(domain)
for page in pages:
record = {'loc': page['url'], 'id': page['id'], 'name': page['name']}
@@ -860,7 +860,7 @@ class Website(models.Model):
record['lastmod'] = page['write_date'].date()
yield record
def get_website_pages(self, domain=[], order='name', limit=None):
def _get_website_pages(self, domain=[], order='name', limit=None):
domain += self.get_current_website().website_domain()
pages = self.env['website.page'].sudo().search(domain, order=order, limit=limit)
return pages
@@ -868,7 +868,7 @@ class Website(models.Model):
def search_pages(self, needle=None, limit=None):
name = slugify(needle, max_length=50, path=True)
res = []
for page in self.enumerate_pages(query_string=name, force=True):
for page in self._enumerate_pages(query_string=name, force=True):
res.append(page)
if len(res) == limit:
break
+1 -1
View File
@@ -25,7 +25,7 @@ class Menu(models.Model):
for menu in self:
if menu.is_mega_menu:
if not menu.mega_menu_content:
default_content = self.env['ir.ui.view'].render_template('website.s_mega_menu_multi_menus')
default_content = self.env['ir.ui.view']._render_template('website.s_mega_menu_multi_menus')
menu.mega_menu_content = default_content.decode()
else:
menu.mega_menu_content = False
+1 -1
View File
@@ -32,7 +32,7 @@ class TestQweb(TransactionCaseWithUserDemo):
demo_env = self.env(user=demo)
html = demo_env['ir.qweb'].render('website.test_template', {"user": demo}, website_id= website.id)
html = demo_env['ir.qweb']._render('website.test_template', {"user": demo}, website_id= website.id)
html = html.strip().decode('utf8')
html = re.sub(r'\?unique=[^"]+', '', html).encode('utf8')
+2 -2
View File
@@ -204,7 +204,7 @@ class TestViewSaving(common.TransactionCase):
)
self.assertIn(
replacement,
view.render().decode('utf-8'),
view._render().decode('utf-8'),
'inline script should not be escaped when rendering'
)
# common text nodes should be be escaped client side
@@ -213,7 +213,7 @@ class TestViewSaving(common.TransactionCase):
self.assertIn(replacement, view.arch, 'common text node should not be escaped server side')
self.assertIn(
replacement,
view.render().decode('utf-8').replace(u'&', u'&amp;'),
view._render().decode('utf-8').replace(u'&', u'&amp;'),
'text node characters wrongly unescaped when rendering'
)
+1 -1
View File
@@ -299,4 +299,4 @@ class WebsiteBlog(http.Controller):
if domain:
dom = expression.AND([dom, domain])
posts = request.env['blog.post'].search(dom, limit=limit, order=order)
return request.website.viewref(template).render({'posts': posts})
return request.website.viewref(template)._render({'posts': posts})
+2 -2
View File
@@ -258,7 +258,7 @@ class WebsiteEventController(http.Controller):
"date": self.get_formated_date(event),
"event": event,
"url": event.website_url})
return request.env['ir.ui.view'].render_template("website_event.country_events_list", result)
return request.env['ir.ui.view']._render_template("website_event.country_events_list", result)
def _process_tickets_form(self, event, form_details):
""" Process posted data about ticket order. Generic ticket are supported
@@ -302,7 +302,7 @@ class WebsiteEventController(http.Controller):
availability_check = False
if not tickets:
return False
return request.env['ir.ui.view'].render_template("website_event.registration_attendee_details", {'tickets': tickets, 'event': event, 'availability_check': availability_check})
return request.env['ir.ui.view']._render_template("website_event.registration_attendee_details", {'tickets': tickets, 'event': event, 'availability_check': availability_check})
def _process_attendees_form(self, event, form_details):
""" Process data posted from the attendee details form.
@@ -42,7 +42,7 @@ class Job(models.Model):
def _get_default_website_description(self):
default_description = self.env["ir.model.data"].xmlid_to_object("website_hr_recruitment.default_website_description")
return (default_description.render() if default_description else "")
return (default_description._render() if default_description else "")
website_description = fields.Html('Website description', translate=html_translate, sanitize_attributes=False, default=_get_default_website_description, prefetch=False, sanitize_form=False)
@@ -203,7 +203,7 @@ class MailGroup(http.Controller):
'msg_more_count': message_count - self._replies_per_page,
'replies_per_page': self._replies_per_page,
}
return request.env.ref('website_mail_channel.messages_short').render(values, engine='ir.qweb')
return request.env.ref('website_mail_channel.messages_short')._render(values, engine='ir.qweb')
@http.route("/groups/<int:group_id>/get_alias_info", type='json', auth='public', website=True)
def get_alias_info(self, group_id, **post):
@@ -9,7 +9,7 @@ class MassMailingPopup(models.Model):
_description = "Mailing list popup"
def _default_popup_content(self):
return self.env['ir.ui.view'].render_template('website_mass_mailing.s_newsletter_block')
return self.env['ir.ui.view']._render_template('website_mass_mailing.s_newsletter_block')
mailing_list_id = fields.Many2one('mailing.list')
website_id = fields.Many2one('website')
+5 -5
View File
@@ -466,12 +466,12 @@ class WebsiteSale(http.Controller):
if not display:
return value
value['website_sale.cart_lines'] = request.env['ir.ui.view'].render_template("website_sale.cart_lines", {
value['website_sale.cart_lines'] = request.env['ir.ui.view']._render_template("website_sale.cart_lines", {
'website_sale_order': order,
'date': fields.Date.today(),
'suggested_products': order._cart_accessories()
})
value['website_sale.short_cart_summary'] = request.env['ir.ui.view'].render_template("website_sale.short_cart_summary", {
value['website_sale.short_cart_summary'] = request.env['ir.ui.view']._render_template("website_sale.short_cart_summary", {
'website_sale_order': order,
})
return value
@@ -960,7 +960,7 @@ class WebsiteSale(http.Controller):
return {
'recall': order.get_portal_last_transaction().state == 'pending',
'message': request.env['ir.ui.view'].render_template("website_sale.payment_confirmation_status", {
'message': request.env['ir.ui.view']._render_template("website_sale.payment_confirmation_status", {
'order': order
})
}
@@ -1025,7 +1025,7 @@ class WebsiteSale(http.Controller):
def print_saleorder(self, **kwargs):
sale_order_id = request.session.get('sale_last_order_id')
if sale_order_id:
pdf, _ = request.env.ref('sale.action_report_saleorder').sudo().render_qweb_pdf([sale_order_id])
pdf, _ = request.env.ref('sale.action_report_saleorder').sudo()._render_qweb_pdf([sale_order_id])
pdfhttpheaders = [('Content-Type', 'application/pdf'), ('Content-Length', u'%s' % len(pdf))]
return request.make_response(pdf, headers=pdfhttpheaders)
else:
@@ -1243,7 +1243,7 @@ class WebsiteSale(http.Controller):
res_product.update(combination_info)
res_product['price'] = FieldMonetary.value_to_html(res_product['price'], monetary_options)
if rating:
res_product['rating'] = request.env["ir.ui.view"].render_template('portal_rating.rating_widget_stars_static', values={
res_product['rating'] = request.env["ir.ui.view"]._render_template('portal_rating.rating_widget_stars_static', values={
'rating_avg': product.rating_avg,
'rating_count': product.rating_count,
})
+1 -1
View File
@@ -14,7 +14,7 @@ class WebsiteSaleVariantController(VariantController):
kw.pop('pricelist_id')
res = self.get_combination_info(product_template_id, product_id, combination, add_qty, request.website.get_current_pricelist(), **kw)
carousel_view = request.env['ir.ui.view'].render_template('website_sale.shop_product_carousel',
carousel_view = request.env['ir.ui.view']._render_template('website_sale.shop_product_carousel',
values={
'product': request.env['product.template'].browse(res['product_template_id']),
'product_variant': request.env['product.product'].browse(res['product_id']),
@@ -30,7 +30,7 @@ class WebsiteSaleProductComparison(WebsiteSale):
prods.mapped('name')
for prod in prods:
ret[prod.id] = {
'render': request.env['ir.ui.view'].render_template(
'render': request.env['ir.ui.view']._render_template(
"website_sale_comparison.product_product",
{'product': prod, 'website': request.website}
),
+1 -1
View File
@@ -858,7 +858,7 @@ class WebsiteSlides(WebsiteProfile):
'comment': answer['comment']
}) for answer in answer_ids]
})
return request.env.ref('website_slides.lesson_content_quiz_question').render({
return request.env.ref('website_slides.lesson_content_quiz_question')._render({
'slide': slide,
'question': slide_question,
})
@@ -123,7 +123,7 @@ class SlideChannelInvite(models.TransientModel):
'model_description': self.env['ir.model']._get('website_slides.slide_channel').display_name,
'company': self.env.company,
}
body = template.render(template_ctx, engine='ir.qweb', minimal_qcontext=True)
body = template._render(template_ctx, engine='ir.qweb', minimal_qcontext=True)
mail_values['body_html'] = self.env['mail.render.mixin']._replace_local_links(body)
return mail_values
+15 -15
View File
@@ -370,7 +370,7 @@ class IrActionsReport(models.Model):
# set context language to body language
if node.get('data-oe-lang'):
layout_with_lang = layout_with_lang.with_context(lang=node.get('data-oe-lang'))
body = layout_with_lang.render(dict(subst=False, body=lxml.html.tostring(node), base_url=base_url))
body = layout_with_lang._render(dict(subst=False, body=lxml.html.tostring(node), base_url=base_url))
bodies.append(body)
if node.get('data-oe-model') == self.model:
res_ids.append(int(node.get('data-oe-id', 0)))
@@ -388,8 +388,8 @@ class IrActionsReport(models.Model):
if attribute[0].startswith('data-report-'):
specific_paperformat_args[attribute[0]] = attribute[1]
header = layout.render(dict(subst=True, body=lxml.html.tostring(header_node), base_url=base_url))
footer = layout.render(dict(subst=True, body=lxml.html.tostring(footer_node), base_url=base_url))
header = layout._render(dict(subst=True, body=lxml.html.tostring(header_node), base_url=base_url))
footer = layout._render(dict(subst=True, body=lxml.html.tostring(footer_node), base_url=base_url))
return bodies, res_ids, header, footer, specific_paperformat_args
@@ -533,7 +533,7 @@ class IrActionsReport(models.Model):
"""
return {}
def render_template(self, template, values=None):
def _render_template(self, template, values=None):
"""Allow to render a QWeb template python-side. This function returns the 'ir.ui.view'
render but embellish it with some variables/methods used in reports.
:param values: additional methods/variables used in the rendering
@@ -561,7 +561,7 @@ class IrActionsReport(models.Model):
website=website,
web_base_url=self.env['ir.config_parameter'].sudo().get_param('web.base.url', default=''),
)
return view_obj.render_template(template, values)
return view_obj._render_template(template, values)
def _post_pdf(self, save_in_attachment, pdf_content=None, res_ids=None):
'''Merge the existing attachments by adding one by one the content of the attachments
@@ -678,7 +678,7 @@ class IrActionsReport(models.Model):
writer.write(result_stream)
return result_stream.getvalue()
def render_qweb_pdf(self, res_ids=None, data=None):
def _render_qweb_pdf(self, res_ids=None, data=None):
if not data:
data = {}
data.setdefault('report_type', 'pdf')
@@ -686,7 +686,7 @@ class IrActionsReport(models.Model):
# In case of test environment without enough workers to perform calls to wkhtmltopdf,
# fallback to render_html.
if (tools.config['test_enable'] or tools.config['test_file']) and not self.env.context.get('force_report_rendering'):
return self.render_qweb_html(res_ids, data=data)
return self._render_qweb_html(res_ids, data=data)
# As the assets are generated during the same transaction as the rendering of the
# templates calling them, there is a scenario where the assets are unreachable: when
@@ -713,7 +713,7 @@ class IrActionsReport(models.Model):
# an asset bundle during the execution of test scenarios. In this case, return
# the html version.
if isinstance(self.env.cr, TestCursor):
return self.with_context(context).render_qweb_html(res_ids, data=data)[0]
return self.with_context(context)._render_qweb_html(res_ids, data=data)[0]
save_in_attachment = OrderedDict()
if res_ids:
@@ -747,7 +747,7 @@ class IrActionsReport(models.Model):
# bypassed
raise UserError(_("Unable to find Wkhtmltopdf on this system. The PDF can not be created."))
html = self.with_context(context).render_qweb_html(res_ids, data=data)[0]
html = self.with_context(context)._render_qweb_html(res_ids, data=data)[0]
# Ensure the current document is utf-8 encoded.
html = html.decode('utf-8')
@@ -772,22 +772,22 @@ class IrActionsReport(models.Model):
return pdf_content, 'pdf'
@api.model
def render_qweb_text(self, docids, data=None):
def _render_qweb_text(self, docids, data=None):
if not data:
data = {}
data.setdefault('report_type', 'text')
data = self._get_rendering_context(docids, data)
return self.render_template(self.report_name, data), 'text'
return self._render_template(self.report_name, data), 'text'
@api.model
def render_qweb_html(self, docids, data=None):
def _render_qweb_html(self, docids, data=None):
"""This method generates and returns html version of a report.
"""
if not data:
data = {}
data.setdefault('report_type', 'html')
data = self._get_rendering_context(docids, data)
return self.render_template(self.report_name, data), 'html'
return self._render_template(self.report_name, data), 'html'
@api.model
def _get_rendering_context_model(self):
@@ -813,9 +813,9 @@ class IrActionsReport(models.Model):
})
return data
def render(self, res_ids, data=None):
def _render(self, res_ids, data=None):
report_type = self.report_type.lower().replace('-', '_')
render_func = getattr(self, 'render_' + report_type, None)
render_func = getattr(self, '_render_' + report_type, None)
if not render_func:
return None
return render_func(res_ids, data=data)
+7 -6
View File
@@ -36,7 +36,7 @@ class IrQWeb(models.AbstractModel, QWeb):
_description = 'Qweb'
@api.model
def render(self, id_or_xml_id, values=None, **options):
def _render(self, id_or_xml_id, values=None, **options):
""" render(id_or_xml_id, values, **options)
Render the template specified by the given name.
@@ -55,7 +55,7 @@ class IrQWeb(models.AbstractModel, QWeb):
context = dict(self.env.context, dev_mode='qweb' in tools.config['dev_mode'])
context.update(options)
result = super(IrQWeb, self).render(id_or_xml_id, values=values, **context)
result = super(IrQWeb, self)._render(id_or_xml_id, values=values, **context)
if b'data-pagebreak=' not in result:
return result
@@ -112,15 +112,16 @@ class IrQWeb(models.AbstractModel, QWeb):
pass
return super(IrQWeb, self).compile(id_or_xml_id, options=options)
def load(self, name, options):
def _load(self, name, options):
lang = options.get('lang', get_lang(self.env).code)
env = self.env
if lang != env.context.get('lang'):
env = env(context=dict(env.context, lang=lang))
template = env['ir.ui.view'].sudo().read_template(name)
view_id = self.env['ir.ui.view'].get_view_id(name)
template = env['ir.ui.view'].sudo()._read_template(view_id)
# QWeb's `read_template` will check if one of the first children of
# QWeb's `_read_template` will check if one of the first children of
# what we send to it has a "t-name" attribute having `name` as value
# to consider it has found it. As it'll never be the case when working
# with view ids or children view or children primary views, force it here.
@@ -323,7 +324,7 @@ class IrQWeb(models.AbstractModel, QWeb):
from odoo.addons.web.controllers.main import module_boot
return json.dumps(module_boot())
return '[]'
template = IrQweb.render(xmlid, {"get_modules_order": get_modules_order})
template = IrQweb._render(xmlid, {"get_modules_order": get_modules_order})
files = []
remains = []
+2 -2
View File
@@ -681,7 +681,7 @@ class Contact(models.AbstractModel):
'object': value,
'options': options
}
return self.env['ir.qweb'].render('base.contact', val, **options.get('template_options', dict()))
return self.env['ir.qweb']._render('base.contact', val, **options.get('template_options', dict()))
class QwebView(models.AbstractModel):
@@ -700,4 +700,4 @@ class QwebView(models.AbstractModel):
_logger.warning("%s.%s must be a 'ir.ui.view' model." % (record, field_name))
return None
return pycompat.to_text(view.render(options.get('values', {}), engine='ir.qweb'))
return pycompat.to_text(view._render(options.get('values', {}), engine='ir.qweb'))
+14 -4
View File
@@ -1491,6 +1491,9 @@ actual arch.
@api.model
def read_template(self, xml_id):
""" Return a template content based on external id
Read access on ir.ui.view required
"""
return self._read_template(self.get_view_id(xml_id))
@api.model
@@ -1599,16 +1602,23 @@ actual arch.
return '%s.%s' % (xmlid['module'], xmlid['name'])
@api.model
def render_template(self, template, values=None, engine='ir.qweb'):
return self.browse(self.get_view_id(template)).render(values, engine)
def render_public_asset(self, template, values=None):
if template not in PUBLIC_ASSETS:
_logger.warning("Add the external id %s in global variable PUBLC_ASSSETS to make the arch accessible in RPC", template)
raise ValidationError(_("Asset %s not accessible") % template)
template = self.browse(self.get_view_id(template))
return template.sudo()._render(values, engine="ir.qweb")
def render(self, values=None, engine='ir.qweb', minimal_qcontext=False):
def _render_template(self, template, values=None, engine='ir.qweb'):
return self.browse(self.get_view_id(template))._render(values, engine)
def _render(self, values=None, engine='ir.qweb', minimal_qcontext=False):
assert isinstance(self.id, int)
qcontext = dict() if minimal_qcontext else self._prepare_qcontext()
qcontext.update(values or {})
return self.env[engine].render(self.id, qcontext)
return self.env[engine]._render(self.id, qcontext)
@api.model
def _prepare_qcontext(self):
+3 -3
View File
@@ -240,7 +240,7 @@ class QWeb(object):
'link', 'menuitem', 'meta', 'param', 'source', 'track', 'wbr'])
_name_gen = count()
def render(self, template, values=None, **options):
def _render(self, template, values=None, **options):
""" render(template, values, **options)
Render the template specified by the given name.
@@ -351,7 +351,7 @@ class QWeb(object):
return (document, template)
else:
try:
document = options.get('load', self.load)(template, options)
document = options.get('load', self._load)(template, options)
except QWebException as e:
raise e
except Exception as e:
@@ -375,7 +375,7 @@ class QWeb(object):
return (node, document)
return (element, document)
def load(self, template, options):
def _load(self, template, options):
""" Load a given template. """
return template
+25 -25
View File
@@ -25,7 +25,7 @@ class TestQWebTField(TransactionCase):
field = etree.Element('span', {'t-field': u'company.name'})
company = self.env['res.company'].create({'name': "My Test Company"})
result = self.engine.render(field, {'company': company})
result = self.engine._render(field, {'company': company})
self.assertEqual(
etree.fromstring(result),
etree.fromstring(u'<span data-oe-model="res.company" data-oe-id="%d" '
@@ -41,7 +41,7 @@ class TestQWebTField(TransactionCase):
s = u"Testing «ταБЬℓσ»: 1<2 & 4+1>3, now 20% off!"
company = self.env['res.company'].create({'name': s})
result = self.engine.render(field, {'company': company})
result = self.engine._render(field, {'company': company})
self.assertEqual(
etree.fromstring(result),
etree.fromstring(u'<span data-oe-model="res.company" data-oe-id="%d" '
@@ -56,13 +56,13 @@ class TestQWebTField(TransactionCase):
field = etree.Element('td', {'t-field': u'company.name'})
with self.assertRaisesRegex(QWebException, r'^RTE widgets do not work correctly'):
self.engine.render(field, {'company': None})
self.engine._render(field, {'company': None})
def test_reject_t_tag(self):
field = etree.Element('t', {'t-field': u'company.name'})
with self.assertRaisesRegex(QWebException, r'^t-field can not be used on a t element'):
self.engine.render(field, {'company': None})
self.engine._render(field, {'company': None})
def test_render_t_options(self):
view1 = self.env['ir.ui.view'].create({
@@ -72,7 +72,7 @@ class TestQWebTField(TransactionCase):
<t t-name="base.dummy"><root><span t-esc="5" t-options="{'widget': 'char'}" t-options-widget="'float'" t-options-precision="4"/></root></t>
"""
})
text = etree.fromstring(view1.render()).find('span').text
text = etree.fromstring(view1._render()).find('span').text
self.assertEqual(text, u'5.0000')
def test_xss_breakout(self):
@@ -88,7 +88,7 @@ class TestQWebTField(TransactionCase):
</t>
"""
})
rendered = view.render({'malicious': '1</script><script>alert("pwned")</script><script>'}).decode()
rendered = view._render({'malicious': '1</script><script>alert("pwned")</script><script>'}).decode()
self.assertIn('alert', rendered, "%r doesn't seem to be rendered" % rendered)
doc = etree.fromstring(rendered)
self.assertEqual(len(doc.xpath('//script')), 1)
@@ -119,7 +119,7 @@ class TestQWebNS(TransactionCase):
""" % expected_result
})
self.assertEqual(etree.fromstring(view1.render()), etree.fromstring(expected_result))
self.assertEqual(etree.fromstring(view1._render()), etree.fromstring(expected_result))
def test_render_static_xml_with_namespace_2(self):
""" Test the rendering on a namespaced view with no static content. The resulting string should be untouched.
@@ -157,7 +157,7 @@ class TestQWebNS(TransactionCase):
""" % expected_result
})
self.assertEqual(etree.fromstring(view1.render()), etree.fromstring(expected_result))
self.assertEqual(etree.fromstring(view1._render()), etree.fromstring(expected_result))
def test_render_static_xml_with_useless_distributed_namespace(self):
""" Test that redundant namespaces are stripped upon rendering.
@@ -190,7 +190,7 @@ class TestQWebNS(TransactionCase):
</root>
""")
self.assertEqual(etree.fromstring(view1.render()), expected_result)
self.assertEqual(etree.fromstring(view1._render()), expected_result)
def test_render_static_xml_with_namespace_3(self):
expected_result = u"""
@@ -205,7 +205,7 @@ class TestQWebNS(TransactionCase):
""" % expected_result
})
self.assertEqual(etree.fromstring(view1.render()), etree.fromstring(expected_result))
self.assertEqual(etree.fromstring(view1._render()), etree.fromstring(expected_result))
def test_render_dynamic_xml_with_namespace_t_esc(self):
""" Test that rendering a template containing a node having both an ns declaration and a t-esc attribute correctly
@@ -223,7 +223,7 @@ class TestQWebNS(TransactionCase):
expected_result = etree.fromstring(u"""<Invoice xmlns:cac="urn:oasis:names:specification:ubl:schema:xsd:CommonAggregateComponents-2">test</Invoice>""")
self.assertEqual(etree.fromstring(view1.render()), expected_result)
self.assertEqual(etree.fromstring(view1._render()), expected_result)
def test_render_dynamic_xml_with_namespace_t_esc_with_useless_distributed_namespace(self):
""" Test that rendering a template containing a node having both an ns declaration and a t-esc attribute correctly
@@ -247,7 +247,7 @@ class TestQWebNS(TransactionCase):
</Invoice>
""")
self.assertEqual(etree.fromstring(view1.render()), expected_result)
self.assertEqual(etree.fromstring(view1._render()), expected_result)
def test_render_dynamic_xml_with_namespace_t_attf(self):
""" Test that rendering a template containing a node having both an ns declaration and a t-attf attribute correctly
@@ -287,7 +287,7 @@ class TestQWebNS(TransactionCase):
</root>
""")
self.assertEqual(etree.fromstring(view1.render()), expected_result)
self.assertEqual(etree.fromstring(view1._render()), expected_result)
def test_render_dynamic_xml_with_namespace_t_attf_with_useless_distributed_namespace(self):
""" Test that rendering a template containing a node having both an ns declaration and a t-attf attribute correctly
@@ -329,7 +329,7 @@ class TestQWebNS(TransactionCase):
""")
self.assertEqual(etree.fromstring(view1.render()), expected_result)
self.assertEqual(etree.fromstring(view1._render()), expected_result)
def test_render_dynamic_xml_with_namespace_2(self):
view1 = self.env['ir.ui.view'].create({
@@ -362,7 +362,7 @@ class TestQWebNS(TransactionCase):
</Invoice>
""")
self.assertEqual(etree.fromstring(view1.render({'version_id': 1.0})), expected_result)
self.assertEqual(etree.fromstring(view1._render({'version_id': 1.0})), expected_result)
def test_render_static_xml_with_namespaced_attributes(self):
view1 = self.env['ir.ui.view'].create({
@@ -377,7 +377,7 @@ class TestQWebNS(TransactionCase):
expected_result = etree.fromstring(u"""<cfdi:Comprobante xmlns:cfdi="http://www.sat.gob.mx/cfd/3" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.sat.gob.mx/cfd/3 http://www.sat.gob.mx/sitio_internet/cfd/3/cfdv32.xsd">abc</cfdi:Comprobante>""")
self.assertEqual(etree.fromstring(view1.render()), expected_result)
self.assertEqual(etree.fromstring(view1._render()), expected_result)
def test_render_dynamic_xml_with_namespaced_attributes(self):
view1 = self.env['ir.ui.view'].create({
@@ -392,7 +392,7 @@ class TestQWebNS(TransactionCase):
expected_result = etree.fromstring("""<cfdi:Comprobante xmlns:cfdi="http://www.sat.gob.mx/cfd/3" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.sat.gob.mx/cfd/3 http://www.sat.gob.mx/sitio_internet/cfd/3/cfdv32.xsd">abc</cfdi:Comprobante>""")
self.assertEqual(etree.fromstring(view1.render()), expected_result)
self.assertEqual(etree.fromstring(view1._render()), expected_result)
def test_render_static_xml_with_t_call(self):
view1 = self.env['ir.ui.view'].create({
@@ -426,7 +426,7 @@ class TestQWebNS(TransactionCase):
"""
})
result = view2.render()
result = view2._render()
result_etree = etree.fromstring(result)
# check that the root tag has all its xmlns
@@ -490,7 +490,7 @@ class TestQWebNS(TransactionCase):
""")
self.assertEqual(
etree.fromstring(view1.with_context(check_view_ids=[view1.id, view2.id]).render()),
etree.fromstring(view1.with_context(check_view_ids=[view1.id, view2.id])._render()),
expected_result
)
@@ -516,7 +516,7 @@ class TestQWebNS(TransactionCase):
error_msg = e.args[0]
with self.assertRaises(QWebException, msg=error_msg):
view1.render()
view1._render()
def test_render_t_call_propagates_t_lang(self):
current_lang = 'en_US'
@@ -554,7 +554,7 @@ class TestQWebNS(TransactionCase):
""" % other_lang
})
rendered = view2.with_context(lang=current_lang).render().strip()
rendered = view2.with_context(lang=current_lang)._render().strip()
self.assertEqual(rendered, b'9/000/000*00')
@@ -622,7 +622,7 @@ class TestQWeb(TransactionCase):
result = doc.find('result[@id="{}"]'.format(template)).text
self.assertEqual(
qweb.render(template, values=params, load=loader).strip(),
qweb._render(template, values=params, load=loader).strip(),
(result or u'').strip().encode('utf-8'),
template
)
@@ -646,7 +646,7 @@ class TestPageSplit(TransactionCase):
</t>
'''
})
rendered = html.fromstring(self.env['ir.qweb'].render(t.id))
rendered = html.fromstring(self.env['ir.qweb']._render(t.id))
ref = E.div(
E.table(E.tr()),
E.div({'style': 'page-break-after: always'}),
@@ -669,7 +669,7 @@ class TestPageSplit(TransactionCase):
</t>
'''
})
rendered = html.fromstring(self.env['ir.qweb'].render(t.id))
rendered = html.fromstring(self.env['ir.qweb']._render(t.id))
self.assertTreesEqual(
rendered,
E.div(
@@ -694,7 +694,7 @@ class TestPageSplit(TransactionCase):
</t>
'''
})
rendered = html.fromstring(self.env['ir.qweb'].render(t.id))
rendered = html.fromstring(self.env['ir.qweb']._render(t.id))
self.assertTreesEqual(
rendered,
E.div(E.table(E.tr(), E.tr(), E.tr()))
+1 -1
View File
@@ -28,6 +28,6 @@ class TestReports(odoo.tests.TransactionCase):
report_records = report_records[:1]
# Test report generation
report.render_qweb_html(report_records.ids)
report._render_qweb_html(report_records.ids)
else:
continue
+8 -8
View File
@@ -2855,8 +2855,8 @@ class TestQWebRender(ViewCase):
})
# render view and child view with an id
content1 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id]).render(view1.id)
content2 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id]).render(view2.id)
content1 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id])._render(view1.id)
content2 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id])._render(view2.id)
self.assertEqual(content1, content2)
@@ -2866,14 +2866,14 @@ class TestQWebRender(ViewCase):
self.env.cr.execute("INSERT INTO ir_model_data(name, model, res_id, module)"
"VALUES ('dummy_ext', 'ir.ui.view', %s, 'base')" % view2.id)
content1 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id]).render('base.dummy')
content2 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id]).render('base.dummy_ext')
content1 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id])._render('base.dummy')
content2 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id])._render('base.dummy_ext')
self.assertEqual(content1, content2)
# render view and primary extension with an id
content1 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id, view3.id]).render(view1.id)
content3 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id, view3.id]).render(view3.id)
content1 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id, view3.id])._render(view1.id)
content3 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id, view3.id])._render(view3.id)
self.assertNotEqual(content1, content3)
@@ -2881,8 +2881,8 @@ class TestQWebRender(ViewCase):
self.env.cr.execute("INSERT INTO ir_model_data(name, model, res_id, module)"
"VALUES ('dummy_primary_ext', 'ir.ui.view', %s, 'base')" % view3.id)
content1 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id, view3.id]).render('base.dummy')
content3 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id, view3.id]).render('base.dummy_primary_ext')
content1 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id, view3.id])._render('base.dummy')
content3 = self.env['ir.qweb'].with_context(check_view_ids=[view1.id, view2.id, view3.id])._render('base.dummy_primary_ext')
self.assertNotEqual(content1, content3)
@@ -64,7 +64,7 @@ class BaseDocumentLayout(models.TransientModel):
for wizard in self:
if wizard.report_layout_id:
ir_qweb = wizard.env['ir.qweb']
wizard.preview = ir_qweb.render('base.layout_preview', {'company': wizard})
wizard.preview = ir_qweb._render('base.layout_preview', {'company': wizard})
else:
wizard.preview = False
@@ -10,4 +10,4 @@ class TestAssetsBundleController(Controller):
env = request.env(user=SUPERUSER_ID)
bundle = env.ref('test_assetsbundle.bundle1')
views = env['ir.ui.view'].search([('inherit_id', '=', bundle.id)])
return views.with_context(check_view_ids=views.ids).render_template('test_assetsbundle.template1')
return views.with_context(check_view_ids=views.ids)._render_template('test_assetsbundle.template1')
@@ -471,7 +471,7 @@ class TestJavascriptAssetsBundle(FileTouchable):
self.assertEqual(len(css_bundle), 1)
def test_20_exteral_lib_assets(self):
html = self.env['ir.ui.view'].render_template('test_assetsbundle.template2')
html = self.env['ir.ui.view']._render_template('test_assetsbundle.template2')
attachments = self.env['ir.attachment'].search([('url', '=like', '/web/content/%-%/test_assetsbundle.bundle4.%')])
self.assertEqual(len(attachments), 2)
self.assertEqual(html.strip(), ("""<!DOCTYPE html>
@@ -490,7 +490,7 @@ class TestJavascriptAssetsBundle(FileTouchable):
</html>""" % {"js": attachments[0].url, "css": attachments[1].url}).encode('utf8'))
def test_21_exteral_lib_assets_debug_mode(self):
html = self.env['ir.ui.view'].render_template('test_assetsbundle.template2', {"debug": "assets"})
html = self.env['ir.ui.view']._render_template('test_assetsbundle.template2', {"debug": "assets"})
attachments = self.env['ir.attachment'].search([('url', '=like', '/web/content/%-%/test_assetsbundle.bundle4.%')])
self.assertEqual(len(attachments), 0)
self.assertEqual(html.strip(), ("""<!DOCTYPE html>
+1 -1
View File
@@ -1219,7 +1219,7 @@ class Response(werkzeug.wrappers.Response):
"""
env = request.env(user=self.uid or request.uid or odoo.SUPERUSER_ID)
self.qcontext['request'] = request
return env["ir.ui.view"].render_template(self.template, self.qcontext)
return env["ir.ui.view"]._render_template(self.template, self.qcontext)
def flatten(self):
""" Forces the rendering of the response's template, sets the result
+1 -1
View File
@@ -35,7 +35,7 @@ def try_report(cr, uid, rname, ids, data=None, context=None, our_module=None, re
if not report_id:
raise Exception("Required report does not exist: %s" % rname)
res_data, res_format = report_id.render(ids, data=data)
res_data, res_format = report_id._render(ids, data=data)
if not res_data:
raise ValueError("Report %s produced an empty result!" % rname)