Commit e9389f1a authored by Vincent Pelletier's avatar Vincent Pelletier

erp5_hal_json_style: Fix Base_redirect semantics.

As noted in a comment in this BT's Base_redirect implementation, original code
does raise when abort_transaction is true.
Not raising in this implementation means that this script will return to caller,
while it never does on original code.
Also, to add insult to injury, this utterly bogus implementation interferes with
transaction boundaries. So suddenly, a single publication spans over 2
transactions, which can lead to:
- ZODB Connection sharing, breaking transaction isolation
- the second transaction implicitly created by this abort (actually, by the next
transactional connector registration to transaction) may be committed,
in which case anything done after Base_redirect returns will be
persistently committed, against caller's explicitly specified intent, and against
all developer expectations.

NEVER TOUCH TRANSACTION ! Only CMFActivity and unittests are allowed
this level of access (and CMFActivity should be modified out of this exceptional
state).
parent ba3ad323
......@@ -14,10 +14,6 @@ def Base_aqBase(self):
def Base_aqInner(self):
return aq_inner(self)
def Portal_abortTransaction(self):
import transaction
transaction.abort()
def Field_getSubFieldKeyDict(self, field, field_id, key=None):
"""XXX"""
return field.generate_subfield_key(field_id, key=key)
......
......@@ -45,7 +45,10 @@
<item>
<key> <string>text_content_warning_message</string> </key>
<value>
<tuple/>
<tuple>
<string>W: 71, 4: No exception type(s) specified (bare-except)</string>
<string>W: 5, 0: Unused ZSQLBrain imported from Products.ZSQLCatalog.zsqlbrain (unused-import)</string>
</tuple>
</value>
</item>
<item>
......
......@@ -3,14 +3,10 @@
:param keep_items: is used mainly to pass "portal_status_message" to be showed to the user
the new UI supports "portal_status_level" with values "success" or "error"
"""
from zExceptions import Redirect
from ZTUtils import make_query
import json
if abort_transaction:
# Old UI simply throws a Redirect exception and Published does its job
# but we cannot use it here so we abort using External Method
context.getPortalObject().Portal_abortTransaction()
request_form = context.REQUEST.form
request_form.update(kw)
request_form = context.ERP5Site_filterParameterList(request_form)
......@@ -34,7 +30,7 @@ if len(parameters):
response = context.REQUEST.RESPONSE
context.Base_prepareCorsResponse(RESPONSE=response)
# http://en.wikipedia.org/wiki/Post/Redirect/Get
response.setStatus(201)
response.setStatus(201, lock=True)
response.setHeader("X-Location", "urn:jio:get:%s" % context.getRelativeUrl())
# be explicit with the reponse content type because in case of reports - they
# can be in text/plain, application/pdf ... so the RJS form needs to know what
......@@ -59,4 +55,8 @@ result_dict = {
}
}
}
return json.dumps(result_dict, indent=2)
result = json.dumps(result_dict, indent=2)
if abort_transaction:
response.write(result)
raise Redirect
return result
<?xml version="1.0"?>
<ZopeData>
<record id="1" aka="AAAAAAAAAAE=">
<pickle>
<global name="ExternalMethod" module="Products.ExternalMethod.ExternalMethod"/>
</pickle>
<pickle>
<dictionary>
<item>
<key> <string>_function</string> </key>
<value> <string>Portal_abortTransaction</string> </value>
</item>
<item>
<key> <string>_module</string> </key>
<value> <string>HalStyle</string> </value>
</item>
<item>
<key> <string>id</string> </key>
<value> <string>Portal_abortTransaction</string> </value>
</item>
<item>
<key> <string>title</string> </key>
<value> <string>Abort Current Transaction</string> </value>
</item>
</dictionary>
</pickle>
</record>
</ZopeData>
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