Reputation: 66380
class Generator(Resource):
@admin_required
def get(self):
pass
If I add the @admin_required decorator on my view, the unit test start failing, with the message:
RuntimeError: working outside of request context
Is there a way to mock it or bypass it for unit tests?
Here is the decorator:
def admin_required(func):
"""Requires App Engine admin credentials"""
@wraps(func)
def decorated_view(*args, **kwargs):
if users.get_current_user():
if not users.is_current_user_admin():
abort(401) # Unauthorized
return func(*args, **kwargs)
return redirect(users.create_login_url(request.url))
return decorated_view
Upvotes: 1
Views: 576
Reputation: 310187
I'd just patch the users module:
from google.appengine.api import users
# ...
@mock.patch.object(users, 'get_current_user')
@mock.patch.object(users, 'is_current_user_admin', return_value=True)
def test_handler(mock_get_current_user, mock_is_current_user_admin):
invoke_your_handler()
# make assertions, etc.
If you want to go deeper, you could use that GAE testbed ... Unfortunately, the documentation here seems to be pretty poor and tricky to get right... Based on this answer, it looks like you need to create a testbed instance and then set the environment:
from google.appengine.ext import testbed
testbed = testbed.TestBed()
testbed.activate()
testbed.init_user_stub()
# Sets environment variables...
testbed.setup_env(
user_email='[email protected]',
user_id='123456',
user_is_admin='1', # '1' is an admin, '0' is a non-admin.
overwrite=True,
)
Now continue your test as usual. If you are using unittest
for testing, you'd probably want to pack all of that fun stuff into your setUp
method.
Also note, in order to avoid polluting your environment, you'll want to call testbed.deactivate()
at the end of the test.
Upvotes: 3