Commit 898ad658 authored by Jérome Perrin's avatar Jérome Perrin

deferred_style: Properly keep request parameters

When rendering reports, deferred style was only keeping request.other, but
some places, like Products.ERP5Form.ListBox.ListBox.getParamDict read only in
request.form, which caused different behaviours when rendering reports
directly or in activities, because when rendering in activities request keys
that the report dialog might have pushed were not preset in request. They
were of course present when rendering the report directly, because this was
the same request, so this lead to different behaviours wether reports were
rendering in activities or directly, like we could observe in 7058ab6f
(accounting: fix grouping option of GL when running in deferred mode, 2021-02-25)

This change deferred style to properly propagate request.other and
request.form in all activities of reports.
parent b96ec371
Pipeline #14173 failed with stage
in 0 seconds
...@@ -50,7 +50,7 @@ for idx, report_data in enumerate(getattr(context, report_configuration_script_i ...@@ -50,7 +50,7 @@ for idx, report_data in enumerate(getattr(context, report_configuration_script_i
# erp5 report # erp5 report
report_active_context.Base_computeReportSection( report_active_context.Base_computeReportSection(
form=report_data['form_id'], form=report_data['form_id'],
request_other=report_data['parameters'], report_request=report_data['parameters'],
user_name=None, user_name=None,
tag=tag, tag=tag,
skin_name=report_data['skin_name'], skin_name=report_data['skin_name'],
......
...@@ -25,7 +25,7 @@ skin_name = request['deferred_portal_skin'] ...@@ -25,7 +25,7 @@ skin_name = request['deferred_portal_skin']
# save request parameters (after calling the report_method which may tweak the # save request parameters (after calling the report_method which may tweak the
# request). # request).
request_other = portal.ERP5Site_filterRequestForDeferredStyle(request) report_request = portal.ERP5Site_filterRequestForDeferredStyle(request)
localizer_language = portal.Localizer.get_selected_language() localizer_language = portal.Localizer.get_selected_language()
...@@ -37,7 +37,7 @@ context.activate( ...@@ -37,7 +37,7 @@ context.activate(
priority=priority, priority=priority,
).Base_computeReportSection( ).Base_computeReportSection(
form=form.getId(), form=form.getId(),
request_other=request_other, report_request=report_request,
user_name=user.getId(), user_name=user.getId(),
tag=tag, tag=tag,
skin_name=skin_name, skin_name=skin_name,
......
...@@ -5,7 +5,8 @@ if notify_report_complete_kwargs is None: ...@@ -5,7 +5,8 @@ if notify_report_complete_kwargs is None:
form = context.restrictedTraverse(form) form = context.restrictedTraverse(form)
request = container.REQUEST request = container.REQUEST
request.other.update(request_other) request.form.update(report_request)
request.other.update(report_request)
with portal.Localizer.translationContext(localizer_language): with portal.Localizer.translationContext(localizer_language):
if form.meta_type == 'ERP5 Report': if form.meta_type == 'ERP5 Report':
...@@ -20,8 +21,8 @@ with portal.Localizer.translationContext(localizer_language): ...@@ -20,8 +21,8 @@ with portal.Localizer.translationContext(localizer_language):
report_title = portal.Base_translateString((form.getProperty('title'))) report_title = portal.Base_translateString((form.getProperty('title')))
# Rebuild request_other as report section can have modify request content # Rebuild request as report section can have modified request content
request_other = portal.ERP5Site_filterRequestForDeferredStyle(request) report_request = portal.ERP5Site_filterRequestForDeferredStyle(request)
active_process = portal.portal_activities.newActiveProcess() active_process = portal.portal_activities.newActiveProcess()
...@@ -39,7 +40,8 @@ for idx, report_section in enumerate(report_section_list): ...@@ -39,7 +40,8 @@ for idx, report_section in enumerate(report_section_list):
localizer_language=localizer_language, localizer_language=localizer_language,
report_section=report_section, report_section=report_section,
report_section_idx=idx, report_section_idx=idx,
request_other=request_other) report_request=report_request,
)
activity_context = context activity_context = context
if activity_context == portal: if activity_context == portal:
...@@ -56,7 +58,7 @@ activity_context.activate( ...@@ -56,7 +58,7 @@ activity_context.activate(
skin_name=skin_name, skin_name=skin_name,
localizer_language=localizer_language, localizer_language=localizer_language,
title=report_title, title=report_title,
request_other=request_other, report_request=report_request,
form_path=form.getPhysicalPath(), form_path=form.getPhysicalPath(),
user_name=user_name, user_name=user_name,
format=format, format=format,
......
...@@ -50,7 +50,7 @@ ...@@ -50,7 +50,7 @@
</item> </item>
<item> <item>
<key> <string>_params</string> </key> <key> <string>_params</string> </key>
<value> <string>form, request_other, user_name, tag, skin_name, format, priority, localizer_language, notify_report_complete_script_id=\'ERP5Site_notifyReportComplete\', notify_report_complete_kwargs=None, **kw</string> </value> <value> <string>form, report_request, user_name, tag, skin_name, format, priority, localizer_language, notify_report_complete_script_id=\'ERP5Site_notifyReportComplete\', notify_report_complete_kwargs=None, **kw</string> </value>
</item> </item>
<item> <item>
<key> <string>_proxy_roles</string> </key> <key> <string>_proxy_roles</string> </key>
......
request = container.REQUEST request = container.REQUEST
request.other.update(request_other) request.form.update(report_request)
request.other.update(report_request)
portal = context.getPortalObject() portal = context.getPortalObject()
......
...@@ -50,7 +50,7 @@ ...@@ -50,7 +50,7 @@
</item> </item>
<item> <item>
<key> <string>_params</string> </key> <key> <string>_params</string> </key>
<value> <string>localizer_language, skin_name, report_section, report_section_idx, request_other</string> </value> <value> <string>localizer_language, skin_name, report_section, report_section_idx, report_request</string> </value>
</item> </item>
<item> <item>
<key> <string>id</string> </key> <key> <string>id</string> </key>
......
# pylint: disable=redefined-builtin # pylint: disable=redefined-builtin
request = container.REQUEST request = container.REQUEST
request.other.update(request_other) request.form.update(report_request)
request.other.update(report_request)
portal = context.getPortalObject() portal = context.getPortalObject()
ap = portal.restrictedTraverse(active_process_url) ap = portal.restrictedTraverse(active_process_url)
......
...@@ -50,7 +50,7 @@ ...@@ -50,7 +50,7 @@
</item> </item>
<item> <item>
<key> <string>_params</string> </key> <key> <string>_params</string> </key>
<value> <string>active_process_url, skin_name, localizer_language, title, request_other, form_path, user_name, format, report_section_count, notify_report_complete_script_id, notify_report_complete_kwargs</string> </value> <value> <string>active_process_url, skin_name, localizer_language, title, report_request, form_path, user_name, format, report_section_count, notify_report_complete_script_id, notify_report_complete_kwargs</string> </value>
</item> </item>
<item> <item>
<key> <string>_proxy_roles</string> </key> <key> <string>_proxy_roles</string> </key>
......
request_other = {} new_request = {}
for k, v in request.other.items() + request.form.items(): for k, v in request.other.items() + request.form.items():
if k not in ('TraversalRequestNameStack', 'AUTHENTICATED_USER', 'URL', if k not in ('TraversalRequestNameStack', 'AUTHENTICATED_USER', 'URL',
...@@ -11,6 +11,6 @@ for k, v in request.other.items() + request.form.items(): ...@@ -11,6 +11,6 @@ for k, v in request.other.items() + request.form.items():
# Remove FileUpload parameters # Remove FileUpload parameters
elif getattr(v, 'headers', ''): elif getattr(v, 'headers', ''):
continue continue
request_other[k] = v new_request[k] = v
return request_other return new_request
...@@ -26,15 +26,18 @@ ...@@ -26,15 +26,18 @@
# #
############################################################################## ##############################################################################
import textwrap
import unittest import unittest
import textwrap import textwrap
from Products.ERP5Type.tests.ERP5TypeTestCase import ERP5TypeTestCase from Products.ERP5Type.tests.ERP5TypeTestCase import ERP5TypeTestCase
from Products.ERP5Type.tests.utils import createZODBPythonScript from Products.ERP5Type.tests.utils import createZODBPythonScript
from Testing import ZopeTestCase from Testing import ZopeTestCase
from AccessControl.SecurityManagement import newSecurityManager from AccessControl.SecurityManagement import newSecurityManager
from Acquisition import aq_base
from Products.ERP5OOo.tests.utils import Validator from Products.ERP5OOo.tests.utils import Validator
from lxml import html from lxml import html
import email, urlparse, httplib import email, urlparse, httplib
from Products.Formulator.MethodField import Method
class DeferredStyleTestCase(ERP5TypeTestCase, ZopeTestCase.Functional): class DeferredStyleTestCase(ERP5TypeTestCase, ZopeTestCase.Functional):
...@@ -94,9 +97,14 @@ class DeferredStyleTestCase(ERP5TypeTestCase, ZopeTestCase.Functional): ...@@ -94,9 +97,14 @@ class DeferredStyleTestCase(ERP5TypeTestCase, ZopeTestCase.Functional):
self.tic() self.tic()
def beforeTearDown(self): def beforeTearDown(self):
document_ids = list(self.portal.document_module.objectIds()) document_id_list = list(self.portal.document_module.objectIds())
if len(document_ids): if document_id_list:
self.portal.document_module.manage_delObjects(ids=document_ids) self.portal.document_module.manage_delObjects(ids=document_id_list)
test_skin_id_list = [
x for x in self.portal.portal_skins.custom.objectIds()
if 'TestDeferredStyle' in x]
if test_skin_id_list:
self.portal.portal_skins.custom.manage_delObjects(ids=test_skin_id_list)
self.tic() self.tic()
def loginAsUser(self, username): def loginAsUser(self, username):
...@@ -352,6 +360,108 @@ class TestDeferredStyleBase(DeferredStyleTestCase): ...@@ -352,6 +360,108 @@ class TestDeferredStyleBase(DeferredStyleTestCase):
mimetype=self.content_type).getData()) mimetype=self.content_type).getData())
self.tic() self.tic()
def test_report_method_access_request(self):
"""Parameters propagated through the report dialog request form should
be available in selection parameters.
"""
report_form_name = 'ERP5Site_viewTestDeferredStyleRequestIndependenceReport'
get_report_section_script_name = 'ERP5Site_getTestDeferredStyleRequestIndependenceReportSectionList'
report_section_form_name = 'ERP5Site_viewTestDeferredStyleRequestIndependenceReportSection'
get_line_list_script_name = 'ERP5Site_getTestDeferredStyleRequestIndependenceReportLineList'
skin_folder = self.portal.portal_skins.custom
# ERP5 Report
skin_folder.manage_addProduct['ERP5Form'].addERP5Report(report_form_name, report_form_name)
report = getattr(skin_folder, report_form_name)
report.report_method = get_report_section_script_name
report.title = self.id()
report.manage_addField(
id='your_field_from_request',
fieldname='StringField',
title='')
report.your_field_from_request.manage_tales_xmlrpc(
{'default': 'python: "in_report_field: set_in_dialog_request == %s" % context.REQUEST.get("set_in_dialog_request")'})
# XXX we need this because ERP5 Report are not usable, but only
# after they are saved to DB and automatically migrated. The getProperty
# above, which is also what ods_style does, only work after the report
# state is updated.
report.__setstate__(aq_base(getattr(skin_folder, report_form_name)).__getstate__())
self.assertEqual(report.getProperty('title'), self.id())
# Report section method
createZODBPythonScript(
skin_folder,
get_report_section_script_name,
'',
textwrap.dedent(
"""\
from Products.ERP5Form.Report import ReportSection
container.REQUEST.set('set_in_report_method', 'set_in_report_method')
return [ReportSection(form_id='%s',
path=context.getPhysicalPath())]
""" % (report_section_form_name)))
# ERP5 Form for report section, with a listbox using the list method
skin_folder.manage_addProduct['ERP5Form'].addERP5Form(
report_section_form_name, report_section_form_name)
report_section_form = getattr(skin_folder, report_section_form_name)
report_section_form.title = self.id()
report_section_form.manage_addField(
id='listbox',
fieldname='ProxyField',
title='')
report_section_form.listbox.manage_edit_xmlrpc(
dict(form_id='Base_viewFieldLibrary',
field_id='my_view_mode_listbox'))
report_section_form.move_field_group(('listbox',), 'left', 'bottom')
report_section_form.listbox.manage_edit_surcharged_xmlrpc(
{
'selection_name': 'test_%s_selection' % self.id(),
'title': self.id(),
'list_method': Method(get_line_list_script_name),
}
)
# List method script
createZODBPythonScript(
skin_folder,
get_line_list_script_name,
'set_in_dialog_request=None, **kw',
textwrap.dedent(
"""\
from Products.PythonScripts.standard import Object
portal = context.getPortalObject()
return [Object(
uid='new_',
title='in_list_method: set_in_dialog_request == %s, set_in_report_method == %s' % (
set_in_dialog_request,
container.REQUEST.get('set_in_report_method'),
))]
"""))
self.loginAsUser('bob')
self.portal.changeSkin('Deferred')
response = self.publish(
'/%s/person_module/%s?deferred_portal_skin=%s&set_in_dialog_request=set_in_dialog_request'
% (self.portal.getId(), report_form_name, self.skin),
'%s:%s' % (self.username, self.password),)
self.tic()
# inspect the report as text and check the selection was initialized from
# request parameter.
mail_message = email.message_from_string(self.portal.MailHost._last_message[2])
part, = [x for x in mail_message.walk() if x.get_content_type() == self.content_type]
report_as_txt = self.portal.portal_transforms.convertTo(
'text/plain',
part.get_payload(decode=True),
context=self.portal,
mimetype=self.content_type).getData()
self.assertIn(
'in_list_method: set_in_dialog_request == set_in_dialog_request, set_in_report_method == set_in_report_method',
report_as_txt)
self.assertIn('in_report_field: set_in_dialog_request == set_in_dialog_request', report_as_txt)
class TestODSDeferredStyle(TestDeferredStyleBase): class TestODSDeferredStyle(TestDeferredStyleBase):
skin = 'ODS' skin = 'ODS'
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment