Browse Source

Merge branch 'mjpieters-appcontext_ignore_handled_exception'

pull/1367/merge
Markus Unterwaditzer 10 years ago
parent
commit
33bad011c3
  1. 1
      AUTHORS
  2. 2
      CHANGES
  3. 11
      flask/app.py
  4. 12
      flask/ctx.py
  5. 15
      tests/test_appctx.py
  6. 15
      tests/test_reqctx.py

1
AUTHORS

@ -22,6 +22,7 @@ Patches and Suggestions
- Kenneth Reitz
- Keyan Pishdadian
- Marian Sigler
- Martijn Pieters
- Matt Campell
- Matthew Frazier
- Michael van Tellingen

2
CHANGES

@ -63,6 +63,8 @@ Version 1.0
``options`` (issue ``#1288``).
- ``flask.json.jsonify`` now supports the ``datetime.date`` type (pull request
``#1326``).
- Don't leak exception info of already catched exceptions to context teardown
handlers (pull request ``#1393``).
Version 0.10.2
--------------

11
flask/app.py

@ -38,6 +38,9 @@ from ._compat import reraise, string_types, text_type, integer_types
# a lock used for logger initialization
_logger_lock = Lock()
# a singleton sentinel value for parameter defaults
_sentinel = object()
def _make_timedelta(value):
if not isinstance(value, timedelta):
@ -1774,7 +1777,7 @@ class Flask(_PackageBoundObject):
self.save_session(ctx.session, response)
return response
def do_teardown_request(self, exc=None):
def do_teardown_request(self, exc=_sentinel):
"""Called after the actual request dispatching and will
call every as :meth:`teardown_request` decorated function. This is
not actually called by the :class:`Flask` object itself but is always
@ -1785,7 +1788,7 @@ class Flask(_PackageBoundObject):
Added the `exc` argument. Previously this was always using the
current exception information.
"""
if exc is None:
if exc is _sentinel:
exc = sys.exc_info()[1]
funcs = reversed(self.teardown_request_funcs.get(None, ()))
bp = _request_ctx_stack.top.request.blueprint
@ -1795,14 +1798,14 @@ class Flask(_PackageBoundObject):
func(exc)
request_tearing_down.send(self, exc=exc)
def do_teardown_appcontext(self, exc=None):
def do_teardown_appcontext(self, exc=_sentinel):
"""Called when an application context is popped. This works pretty
much the same as :meth:`do_teardown_request` but for the application
context.
.. versionadded:: 0.9
"""
if exc is None:
if exc is _sentinel:
exc = sys.exc_info()[1]
for func in reversed(self.teardown_appcontext_funcs):
func(exc)

12
flask/ctx.py

@ -21,6 +21,10 @@ from .signals import appcontext_pushed, appcontext_popped
from ._compat import BROKEN_PYPY_CTXMGR_EXIT, reraise
# a singleton sentinel value for parameter defaults
_sentinel = object()
class _AppCtxGlobals(object):
"""A plain object."""
@ -168,11 +172,11 @@ class AppContext(object):
_app_ctx_stack.push(self)
appcontext_pushed.send(self.app)
def pop(self, exc=None):
def pop(self, exc=_sentinel):
"""Pops the app context."""
self._refcnt -= 1
if self._refcnt <= 0:
if exc is None:
if exc is _sentinel:
exc = sys.exc_info()[1]
self.app.do_teardown_appcontext(exc)
rv = _app_ctx_stack.pop()
@ -320,7 +324,7 @@ class RequestContext(object):
if self.session is None:
self.session = self.app.make_null_session()
def pop(self, exc=None):
def pop(self, exc=_sentinel):
"""Pops the request context and unbinds it by doing that. This will
also trigger the execution of functions registered by the
:meth:`~flask.Flask.teardown_request` decorator.
@ -334,7 +338,7 @@ class RequestContext(object):
if not self._implicit_app_ctx_stack:
self.preserved = False
self._preserved_exc = None
if exc is None:
if exc is _sentinel:
exc = sys.exc_info()[1]
self.app.do_teardown_request(exc)

15
tests/test_appctx.py

@ -78,6 +78,21 @@ def test_app_tearing_down_with_previous_exception():
assert cleanup_stuff == [None]
def test_app_tearing_down_with_handled_exception():
cleanup_stuff = []
app = flask.Flask(__name__)
@app.teardown_appcontext
def cleanup(exception):
cleanup_stuff.append(exception)
with app.app_context():
try:
raise Exception('dummy')
except Exception:
pass
assert cleanup_stuff == [None]
def test_custom_app_ctx_globals_class():
class CustomRequestGlobals(object):
def __init__(self):

15
tests/test_reqctx.py

@ -48,6 +48,21 @@ def test_teardown_with_previous_exception():
assert buffer == []
assert buffer == [None]
def test_teardown_with_handled_exception():
buffer = []
app = flask.Flask(__name__)
@app.teardown_request
def end_of_request(exception):
buffer.append(exception)
with app.test_request_context():
assert buffer == []
try:
raise Exception('dummy')
except Exception:
pass
assert buffer == [None]
def test_proper_test_request_context():
app = flask.Flask(__name__)
app.config.update(

Loading…
Cancel
Save