Commit 2cc6449a authored by Jérome Perrin's avatar Jérome Perrin

DeferredStyle : allow to send an email containing links to reports instead of the report itself

Backport nexedi/erp5!799

/reviewed-on https://lab.nexedi.com/nexedi/erp5-capago/merge_requests/30
parents f1924b4d dc4bd890
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ActionInformation" module="Products.CMFCore.ActionInformation"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>action</string> </key>
<value>
<persistent> <string encoding="base64">AAAAAAAAAAI=</string> </persistent>
</value>
</item>
<item>
<key> <string>categories</string> </key>
<value>
<tuple>
<string>action_type/object_view</string>
</tuple>
</value>
</item>
<item>
<key> <string>category</string> </key>
<value> <string>object_view</string> </value>
</item>
<item>
<key> <string>condition</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>description</string> </key>
<value>
<none/>
</value>
</item>
<item>
<key> <string>icon</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>deferred_preference</string> </value>
</item>
<item>
<key> <string>permissions</string> </key>
<value>
<tuple>
<string>View</string>
</tuple>
</value>
</item>
<item>
<key> <string>priority</string> </key>
<value> <float>8.0</float> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>Deferred Style</string> </value>
</item>
<item>
<key> <string>visible</string> </key>
<value> <int>1</int> </value>
</item>
</dictionary>
</pickle>
</record>
<record id="2" aka="AAAAAAAAAAI=">
<pickle>
<global name="Expression" module="Products.CMFCore.Expression"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>text</string> </key>
<value> <string>string:${object_url}/SystemPreference_viewDeferredStyle</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Property Sheet" module="erp5.portal_type"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_count</string> </key>
<value>
<persistent> <string encoding="base64">AAAAAAAAAAI=</string> </persistent>
</value>
</item>
<item>
<key> <string>_mt_index</string> </key>
<value>
<persistent> <string encoding="base64">AAAAAAAAAAM=</string> </persistent>
</value>
</item>
<item>
<key> <string>_tree</string> </key>
<value>
<persistent> <string encoding="base64">AAAAAAAAAAQ=</string> </persistent>
</value>
</item>
<item>
<key> <string>description</string> </key>
<value>
<none/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>DeferredStylePreference</string> </value>
</item>
<item>
<key> <string>portal_type</string> </key>
<value> <string>Property Sheet</string> </value>
</item>
</dictionary>
</pickle>
</record>
<record id="2" aka="AAAAAAAAAAI=">
<pickle>
<global name="Length" module="BTrees.Length"/>
</pickle>
<pickle> <int>0</int> </pickle>
</record>
<record id="3" aka="AAAAAAAAAAM=">
<pickle>
<global name="OOBTree" module="BTrees.OOBTree"/>
</pickle>
<pickle>
<none/>
</pickle>
</record>
<record id="4" aka="AAAAAAAAAAQ=">
<pickle>
<global name="OOBTree" module="BTrees.OOBTree"/>
</pickle>
<pickle>
<none/>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Standard Property" module="erp5.portal_type"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>categories</string> </key>
<value>
<tuple>
<string>elementary_type/string</string>
</tuple>
</value>
</item>
<item>
<key> <string>description</string> </key>
<value>
<none/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>preferred_deferred_report_classification_property</string> </value>
</item>
<item>
<key> <string>portal_type</string> </key>
<value> <string>Standard Property</string> </value>
</item>
<item>
<key> <string>preference</string> </key>
<value> <int>1</int> </value>
</item>
<item>
<key> <string>property_default</string> </key>
<value>
<none/>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Standard Property" module="erp5.portal_type"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>categories</string> </key>
<value>
<tuple>
<string>elementary_type/string</string>
</tuple>
</value>
</item>
<item>
<key> <string>description</string> </key>
<value>
<none/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>preferred_deferred_report_notification_message_reference_property</string> </value>
</item>
<item>
<key> <string>portal_type</string> </key>
<value> <string>Standard Property</string> </value>
</item>
<item>
<key> <string>preference</string> </key>
<value> <int>1</int> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Standard Property" module="erp5.portal_type"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>categories</string> </key>
<value>
<tuple>
<string>elementary_type/string</string>
</tuple>
</value>
</item>
<item>
<key> <string>description</string> </key>
<value>
<none/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>preferred_deferred_report_publication_section_property</string> </value>
</item>
<item>
<key> <string>portal_type</string> </key>
<value> <string>Standard Property</string> </value>
</item>
<item>
<key> <string>preference</string> </key>
<value> <int>1</int> </value>
</item>
<item>
<key> <string>property_default</string> </key>
<value>
<none/>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="Standard Property" module="erp5.portal_type"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>categories</string> </key>
<value>
<tuple>
<string>elementary_type/boolean</string>
</tuple>
</value>
</item>
<item>
<key> <string>description</string> </key>
<value>
<none/>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>preferred_deferred_report_stored_as_document_property</string> </value>
</item>
<item>
<key> <string>portal_type</string> </key>
<value> <string>Standard Property</string> </value>
</item>
<item>
<key> <string>preference</string> </key>
<value> <int>1</int> </value>
</item>
<item>
<key> <string>property_default</string> </key>
<value>
<none/>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
......@@ -2,6 +2,10 @@
from Products.ERP5Type.Message import translateString
portal = context.getPortalObject()
request = portal.REQUEST
report_format = request_form.get('format', '')
if portal.portal_preferences.getPreferredDeferredReportStoredAsDocument():
request_form['format'] = None
request.form.update(request_form)
if skin_name and skin_name != 'None': # make_query serializes None as 'None'
......@@ -31,4 +35,5 @@ with portal.Localizer.translationContext(localizer_language):
user_name=user_name,
subject=str(translateString(attachment_name.rsplit('.', 1)[0])),
message='',
attachment_list=attachment_list)
attachment_list=attachment_list,
format=report_format)
......@@ -23,9 +23,12 @@ with portal.Localizer.translationContext(localizer_language):
return data.decode('bz2')
except IOError:
return data.decode('zlib')
if portal.portal_preferences.getPreferredDeferredReportStoredAsDocument():
pt_render_format = None
else:
pt_render_format = format
report_data = context.restrictedTraverse(form_path).report_view.pt_render(
extra_context=dict(options={'format': format},
extra_context=dict(options={'format': pt_render_format},
rendered_report_item_list=(decodeReportSection(r[1]) for r in report_section_list),
report_method=dummyReportMethod,
form=portal.restrictedTraverse(form_path)))
......@@ -52,4 +55,5 @@ portal.ERP5Site_notifyReportComplete(
user_name=user_name,
subject=title,
message='',
attachment_list=attachment_list)
attachment_list=attachment_list,
format=format)
from Products.PythonScripts.standard import newline_to_br, html_quote
portal = context.getPortalObject()
prefs = portal.portal_preferences
report_item_list = []
message_text_format = "text/plain"
pre_convert_tag = 'pre-convert-report-%s' % random.randint(0, 1000)
portal.portal_notifications.activate(activity='SQLQueue').sendMessage(
recipient=user_name,
subject=subject,
message=message,
message_text_format='text/plain',
notifier_list=('Mail Message',),
store_as_event=False,
attachment_list=attachment_list,
)
if prefs.getPreferredDeferredReportStoredAsDocument():
for attachment in attachment_list:
document = portal.portal_contributions.newContent(
data=attachment['content'],
publication_section=prefs.getPreferredDeferredReportPublicationSection(),
classification=prefs.getPreferredDeferredReportClassification(),
filename=attachment['name'],
)
document.share()
report_item_list.append(
(attachment.get('title', document.getStandardFilename(format=format)), document.getRelativeUrl()))
# pre-convert document before sending notification
if format:
document.activate(tag=pre_convert_tag).convert(format=format)
url_base = portal.ERP5Site_getAbsoluteUrl()
attachment_link_list = [
{
'download_link': '%s/%s?format=%s' % (url_base , report_url, format),
'name': report_name
} for (report_name, report_url) in report_item_list
]
message_html = newline_to_br(html_quote(message))
message_text_format = "text/html"
attachment_list = []
notification_message_reference = prefs.getPreferredDeferredReportNotificationMessageReference()
if notification_message_reference:
notification_message = portal.portal_notifications.getDocumentValue(reference=notification_message_reference)
if notification_message is None:
raise ValueError('Notification message not found by %r' % prefs.getPreferredDeferredReportNotificationMessageReference())
notification_mapping_dict = {
'report_link_list': portal.ERP5Site_viewReportCompleteNotificationMessage(
attachment_link_list=attachment_link_list
),
'message': message_html
}
message = notification_message.asEntireHTML(
safe_substitute=False,
substitution_method_parameter_dict={'mapping_dict': notification_mapping_dict})
else:
# fallback to generating message with the page template when no notification message
message = portal.ERP5Site_viewReportCompleteNotificationMessage(
attachment_link_list=attachment_link_list,
message=message_html
)
portal.portal_notifications.activate(after_tag=pre_convert_tag, activity='SQLQueue').sendMessage(
recipient=user_name,
subject=subject,
message=message,
message_text_format=message_text_format,
notifier_list=('Mail Message',),
store_as_event=False,
attachment_list=attachment_list,
)
......@@ -50,7 +50,15 @@
</item>
<item>
<key> <string>_params</string> </key>
<value> <string>user_name, subject, message, attachment_list</string> </value>
<value> <string>user_name, subject, message, attachment_list, format=""</string> </value>
</item>
<item>
<key> <string>_proxy_roles</string> </key>
<value>
<tuple>
<string>Manager</string>
</tuple>
</value>
</item>
<item>
<key> <string>id</string> </key>
......
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ZopePageTemplate" module="Products.PageTemplates.ZopePageTemplate"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_bind_names</string> </key>
<value>
<object>
<klass>
<global name="NameAssignments" module="Shared.DC.Scripts.Bindings"/>
</klass>
<tuple/>
<state>
<dictionary>
<item>
<key> <string>_asgns</string> </key>
<value>
<dictionary>
<item>
<key> <string>name_subpath</string> </key>
<value> <string>traverse_subpath</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</state>
</object>
</value>
</item>
<item>
<key> <string>content_type</string> </key>
<value> <string>text/html</string> </value>
</item>
<item>
<key> <string>expand</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>ERP5Site_viewReportCompleteNotificationMessage</string> </value>
</item>
<item>
<key> <string>output_encoding</string> </key>
<value> <string>utf-8</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <unicode></unicode> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<tal:block xmlns:tal="http://xml.zope.org/namespaces/tal">
<tal:block tal:replace="nothing">
This page template is used to prepare `report_link_list` variable to pass to notification message.
When no notification message exists, this page template acts as a "default notification message" and
receive `message` argument.
</tal:block>
<tal:block tal:condition="options/message | nothing">
<p>
<tal:block tal:replace="structure options/message" />
</p>
</tal:block>
<tal:block tal:repeat="attachment options/attachment_link_list">
<p>
<a tal:attributes="href attachment/download_link" tal:content="attachment/name"></a>
</p>
</tal:block>
</tal:block>
\ No newline at end of file
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ERP5 Form" module="erp5.portal_type"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_bind_names</string> </key>
<value>
<object>
<klass>
<global name="NameAssignments" module="Shared.DC.Scripts.Bindings"/>
</klass>
<tuple/>
<state>
<dictionary>
<item>
<key> <string>_asgns</string> </key>
<value>
<dictionary/>
</value>
</item>
</dictionary>
</state>
</object>
</value>
</item>
<item>
<key> <string>_objects</string> </key>
<value>
<tuple/>
</value>
</item>
<item>
<key> <string>action</string> </key>
<value> <string>Base_edit</string> </value>
</item>
<item>
<key> <string>description</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>edit_order</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>encoding</string> </key>
<value> <string>UTF-8</string> </value>
</item>
<item>
<key> <string>enctype</string> </key>
<value> <string>multipart/form-data</string> </value>
</item>
<item>
<key> <string>group_list</string> </key>
<value>
<list>
<string>left</string>
<string>right</string>
</list>
</value>
</item>
<item>
<key> <string>groups</string> </key>
<value>
<dictionary>
<item>
<key> <string>left</string> </key>
<value>
<list>
<string>my_preferred_deferred_report_stored_as_document</string>
<string>my_preferred_deferred_report_notification_message_reference</string>
<string>my_preferred_deferred_report_classification</string>
<string>my_preferred_deferred_report_publication_section</string>
</list>
</value>
</item>
<item>
<key> <string>right</string> </key>
<value>
<list/>
</value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>SystemPreference_viewDeferredStyle</string> </value>
</item>
<item>
<key> <string>method</string> </key>
<value> <string>POST</string> </value>
</item>
<item>
<key> <string>name</string> </key>
<value> <string>SystemPreference_viewDeferredStyle</string> </value>
</item>
<item>
<key> <string>pt</string> </key>
<value> <string>form_view</string> </value>
</item>
<item>
<key> <string>row_length</string> </key>
<value> <int>4</int> </value>
</item>
<item>
<key> <string>stored_encoding</string> </key>
<value> <string>UTF-8</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>Deferred Style</string> </value>
</item>
<item>
<key> <string>unicode_mode</string> </key>
<value> <int>0</int> </value>
</item>
<item>
<key> <string>update_action</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>update_action_title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ProxyField" module="Products.ERP5Form.ProxyField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>delegated_list</string> </key>
<value>
<list>
<string>items</string>
<string>title</string>
</list>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>my_preferred_deferred_report_classification</string> </value>
</item>
<item>
<key> <string>message_values</string> </key>
<value>
<dictionary>
<item>
<key> <string>external_validator_failed</string> </key>
<value> <string>The input failed the external validator.</string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>overrides</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>tales</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>items</string> </key>
<value>
<persistent> <string encoding="base64">AAAAAAAAAAI=</string> </persistent>
</value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>values</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string>my_category</string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string>Base_viewFieldLibrary</string> </value>
</item>
<item>
<key> <string>items</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string>Click to edit the target</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>Preferred Classification</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</pickle>
</record>
<record id="2" aka="AAAAAAAAAAI=">
<pickle>
<global name="TALESMethod" module="Products.Formulator.TALESField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_text</string> </key>
<value> <string>python: here.portal_categories.classification.getCategoryChildLogicalPathItemList(display_none_category=1,filter_node=1,local_sort_id=\'title\',checked_permission=\'View\')</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ProxyField" module="Products.ERP5Form.ProxyField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>delegated_list</string> </key>
<value>
<list>
<string>display_width</string>
<string>title</string>
</list>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>my_preferred_deferred_report_notification_message_reference</string> </value>
</item>
<item>
<key> <string>message_values</string> </key>
<value>
<dictionary>
<item>
<key> <string>external_validator_failed</string> </key>
<value> <string>The input failed the external validator.</string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>overrides</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>tales</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>values</string> </key>
<value>
<dictionary>
<item>
<key> <string>display_width</string> </key>
<value> <int>20</int> </value>
</item>
<item>
<key> <string>field_id</string> </key>
<value> <string>my_string_field</string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string>Base_viewWizardFieldLibrary</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>Notification Message Reference</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ProxyField" module="Products.ERP5Form.ProxyField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>delegated_list</string> </key>
<value>
<list>
<string>items</string>
<string>title</string>
</list>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>my_preferred_deferred_report_publication_section</string> </value>
</item>
<item>
<key> <string>message_values</string> </key>
<value>
<dictionary>
<item>
<key> <string>external_validator_failed</string> </key>
<value> <string>The input failed the external validator.</string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>overrides</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>tales</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>items</string> </key>
<value>
<persistent> <string encoding="base64">AAAAAAAAAAI=</string> </persistent>
</value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>values</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string>my_category</string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string>Base_viewFieldLibrary</string> </value>
</item>
<item>
<key> <string>items</string> </key>
<value>
<list/>
</value>
</item>
<item>
<key> <string>target</string> </key>
<value> <string>Click to edit the target</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>Preferred Publication Section</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</pickle>
</record>
<record id="2" aka="AAAAAAAAAAI=">
<pickle>
<global name="TALESMethod" module="Products.Formulator.TALESField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_text</string> </key>
<value> <string>python: here.portal_categories.publication_section.getCategoryChildLogicalPathItemList(display_none_category=1,filter_node=1,local_sort_id=\'title\',checked_permission=\'View\')</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ProxyField" module="Products.ERP5Form.ProxyField"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>delegated_list</string> </key>
<value>
<list>
<string>title</string>
</list>
</value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>my_preferred_deferred_report_stored_as_document</string> </value>
</item>
<item>
<key> <string>message_values</string> </key>
<value>
<dictionary>
<item>
<key> <string>external_validator_failed</string> </key>
<value> <string>The input failed the external validator.</string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>overrides</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>tales</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string></string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string></string> </value>
</item>
</dictionary>
</value>
</item>
<item>
<key> <string>values</string> </key>
<value>
<dictionary>
<item>
<key> <string>field_id</string> </key>
<value> <string>my_checkbox</string> </value>
</item>
<item>
<key> <string>form_id</string> </key>
<value> <string>Base_viewFieldLibrary</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>Deferred Report Stored as Document</string> </value>
</item>
</dictionary>
</value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
System Preference | deferred_preference
\ No newline at end of file
DeferredStylePreference
\ No newline at end of file
......@@ -28,10 +28,12 @@
import unittest
from Products.ERP5Type.tests.ERP5TypeTestCase import ERP5TypeTestCase
from Products.ERP5Type.tests.utils import createZODBPythonScript
from Testing import ZopeTestCase
from AccessControl.SecurityManagement import newSecurityManager
from Products.ERP5OOo.tests.utils import Validator
import email
from lxml import html
import email, urlparse, httplib
class TestDeferredStyle(ERP5TypeTestCase, ZopeTestCase.Functional):
......@@ -45,6 +47,8 @@ class TestDeferredStyle(ERP5TypeTestCase, ZopeTestCase.Functional):
# address. Zope 2.12 only surrounds names with quotes if they really need
# quoting.
first_name = 'Bob<Par'
publication_section = "reporting"
classification = "collaborative"
def getTitle(self):
return 'Test Deferred Style'
......@@ -54,6 +58,10 @@ class TestDeferredStyle(ERP5TypeTestCase, ZopeTestCase.Functional):
'erp5_base',
'erp5_ods_style',
'erp5_odt_style',
'erp5_ingestion_mysql_innodb_catalog',
'erp5_ingestion',
'erp5_web',
'erp5_dms',
'erp5_deferred_style',
'erp5_l10n_fr',)
......@@ -76,6 +84,25 @@ class TestDeferredStyle(ERP5TypeTestCase, ZopeTestCase.Functional):
password=self.password,
)
login.validate()
system_preference = self.portal.portal_preferences._getOb('syspref', None)
if system_preference is None:
system_preference = self.portal.portal_preferences.newContent(
id="syspref",
portal_type="System Preference")
system_preference.enable()
# Fallback to former behaviour
system_preference.edit(preferred_deferred_report_stored_as_document=False)
# add categories
if not getattr(self.portal.portal_categories.classification, 'collaborative', None):
self.portal.portal_categories.classification.newContent(id="collaborative")
if not getattr(self.portal.portal_categories.publication_section, 'reporting', None):
self.portal.portal_categories.publication_section.newContent(id="reporting")
self.tic()
def beforeTearDown(self):
document_ids = list(self.portal.document_module.objectIds())
if len(document_ids):
self.portal.document_module.manage_delObjects(ids=document_ids)
self.tic()
def loginAsUser(self, username):
......@@ -117,6 +144,123 @@ class TestDeferredStyle(ERP5TypeTestCase, ZopeTestCase.Functional):
else:
self.fail('Attachment not found in email\n%s' % message_text)
def _checkEmailLink(self, part, extension=None, content_type=None):
content = part.get_payload(decode=True)
self.assertTrue("History%s" % extension or self.attachment_file_extension in content)
tree = html.fromstring(content)
link, = [href for href in tree.xpath('//a/@href') if href]
relative_url =urlparse.urlparse(link)
report = self.publish(relative_url.path+"?"+relative_url.query, '%s:%s' % (self.username, self.password))
self.assertEqual(httplib.OK, report.getStatus())
self.assertEqual(report.getHeader('content-type'), content_type or self.content_type)
def _checkDocument(self):
document_list = self.portal.document_module.objectValues()
self.assertEquals(len(document_list), 1)
document = document_list[0].getObject()
expected_file_name = 'History%s' % self.attachment_file_extension
self.assertEqual(expected_file_name, document.getFilename())
self.assertEqual('History', document.getTitle())
self.assertEqual(None, document.getReference())
self.assertEqual("shared", document.getValidationState())
self.assertEqual(self.publication_section, document.getPublicationSection())
self.assertEqual(self.classification, document.getClassification())
self.assertEqual(self.portal_type, document.getPortalType())
def _defineSystemPreference(self, notification_message_reference=None):
system_preference = self.portal.portal_preferences._getOb('syspref', None)
system_preference.edit(
preferred_deferred_report_stored_as_document=True,
preferred_deferred_report_classification=self.classification,
preferred_deferred_report_publication_section=self.publication_section,
preferred_deferred_report_notification_message_reference=notification_message_reference)
def test_report_stored_as_document(self):
self._defineSystemPreference()
self.loginAsUser('bob')
self.portal.changeSkin('Deferred')
response = self.publish(
'/%s/person_module/pers/Base_viewHistory?deferred_portal_skin=%s'
% (self.portal.getId(), self.skin), '%s:%s' % (self.username, self.password))
self.tic()
self._checkDocument()
last_message = self.portal.MailHost._last_message
self.assertNotEquals((), last_message)
mfrom, mto, message_text = last_message
self.assertEqual('"%s" <%s>' % (self.first_name, self.recipient_email_address), mto[0])
mail_message = email.message_from_string(message_text)
for part in mail_message.walk():
content_type = part.get_content_type()
if content_type == "text/html":
self._checkEmailLink(part)
break
else:
self.fail('Link not found in email\n%s' % message_text)
def test_report_stored_as_document_with_notification_message(self):
createZODBPythonScript(self.portal,
'NotificationMessage_getSubstitutionMappingDictFromArgument',
'mapping_dict',
'''return mapping_dict''')
notification_message = self.portal.notification_message_module.newContent(
reference="notification-deferred.report",
content_type="text/html",
text_content='Hi,\n\nHere is the link(s) to your report(s) : ${report_link_list}.\n\n',
text_content_substitution_mapping_method_id='NotificationMessage_getSubstitutionMappingDictFromArgument',
)
notification_message.newContent(portal_type="Role Definition",
role_name="Auditor",
agent="person_module/pers")
notification_message.validate()
self.tic()
self._defineSystemPreference("notification-deferred.report")
self.loginAsUser('bob')
self.portal.changeSkin('Deferred')
response = self.publish(
'/%s/person_module/pers/Base_viewHistory?deferred_portal_skin=%s'
% (self.portal.getId(), self.skin), '%s:%s' % (self.username, self.password))
self.tic()
self._checkDocument()
last_message = self.portal.MailHost._last_message
self.assertNotEquals((), last_message)
mfrom, mto, message_text = last_message
self.assertEqual('"%s" <%s>' % (self.first_name, self.recipient_email_address), mto[0])
mail_message = email.message_from_string(message_text)
for part in mail_message.walk():
content_type = part.get_content_type()
if content_type == "text/html":
self._checkEmailLink(part)
break
else:
self.fail('Link not found in email\n%s' % message_text)
def test_pdf_report_stored_as_document(self):
self._defineSystemPreference()
self.loginAsUser('bob')
self.portal.changeSkin('Deferred')
response = self.publish(
'/%s/person_module/pers/Base_viewHistory?deferred_portal_skin=%s&format=pdf'
% (self.portal.getId(), self.skin), '%s:%s' % (self.username, self.password))
self.tic()
# A document has been created
self._checkDocument()
last_message = self.portal.MailHost._last_message
self.assertNotEquals((), last_message)
mfrom, mto, message_text = last_message
self.assertEqual('"%s" <%s>' % (self.first_name, self.recipient_email_address), mto[0])
mail_message = email.message_from_string(message_text)
for part in mail_message.walk():
content_type = part.get_content_type()
if content_type == "text/html":
self._checkEmailLink(part, ".pdf", "application/pdf")
break
else:
self.fail('Link not found in email\n%s' % message_text)
def test_normal_form(self):
self.loginAsUser('bob')
# simulate a big request, for which Base_callDialogMethod will not issue a
......@@ -213,6 +357,7 @@ class TestODSDeferredStyle(TestDeferredStyle):
skin = 'ODS'
content_type = 'application/vnd.oasis.opendocument.spreadsheet'
attachment_file_extension = '.ods'
portal_type="Spreadsheet"
def test_report_view_sheet_per_report_section(self):
"""Test the sheet_per_report_section feature of erp5_ods_style.
......@@ -251,11 +396,10 @@ class TestODTDeferredStyle(TestDeferredStyle):
skin = 'ODT'
content_type = 'application/vnd.oasis.opendocument.text'
attachment_file_extension = '.odt'
portal_type = "Text"
def test_suite():
suite = unittest.TestSuite()
suite.addTest(unittest.makeSuite(TestODSDeferredStyle))
suite.addTest(unittest.makeSuite(TestODTDeferredStyle))
return suite
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