Flask with blueprint pattern, using Flask Restful with a Token Resource class and method decorator for jwt_required.
'''In app.py'''
from flask_jwt_extended import JWTManager
from flask import Flask
jwtmanager = JWTManager()
def create_app():
app = Flask(__name__)
def register_extensions(app):
jwtmanager.init_app(app)
'''in views.py'''
from flask_restful import Resource, Api
from flask_jwt_extended import jwt_required
api = Api()
class TokenResource(Resource):
method_decorators = [jwt_required]
class HelloWorld(TokenResource):
def get(self):
return 'Hello, World!'
api.add_resource(HelloWorld, '/hello')
The issue I am having is with exceptions and it likely has little to do with this library. When I run into a common jwt_extended exception on the flask development server with debug enabled I get this which is awesome!
{
"msg": "Token has expired"
}
With Gunicorn I get this on the exact same request with the same expired token.
gunicorn --reload --worker-class "gevent" "app:create_app()"
{"message": "Internal Server Error"}
with a traceback that the development server never showed.
File "/usr/local/lib/python3.5/site-packages/flask/app.py", line 1639, in full_dispatch_request
rv = self.dispatch_request()
File "/usr/local/lib/python3.5/site-packages/flask/app.py", line 1625, in dispatch_request
return self.view_functions[rule.endpoint](**req.view_args)
File "/usr/local/lib/python3.5/site-packages/flask_restful/__init__.py", line 477, in wrapper
resp = resource(*args, **kwargs)
File "/usr/local/lib/python3.5/site-packages/flask/views.py", line 84, in view
return self.dispatch_request(*args, **kwargs)
File "/usr/local/lib/python3.5/site-packages/flask_restful/__init__.py", line 587, in dispatch_request
resp = meth(*args, **kwargs)
File "/usr/local/lib/python3.5/site-packages/flask_jwt_extended/utils.py", line 222, in wrapper
jwt_data = _decode_jwt_from_request(type='access')
File "/usr/local/lib/python3.5/site-packages/flask_jwt_extended/utils.py", line 204, in _decode_jwt_from_request
return _decode_jwt_from_headers()
File "/usr/local/lib/python3.5/site-packages/flask_jwt_extended/utils.py", line 176, in _decode_jwt_from_headers
return _decode_jwt(token, secret, algorithm)
File "/usr/local/lib/python3.5/site-packages/flask_jwt_extended/utils.py", line 136, in _decode_jwt
data = jwt.decode(token, secret, algorithm=algorithm)
File "/usr/local/lib/python3.5/site-packages/jwt/api_jwt.py", line 75, in decode
self._validate_claims(payload, merged_options, **kwargs)
File "/usr/local/lib/python3.5/site-packages/jwt/api_jwt.py", line 104, in _validate_claims
self._validate_exp(payload, now, leeway)
File "/usr/local/lib/python3.5/site-packages/jwt/api_jwt.py", line 149, in _validate_exp
raise ExpiredSignatureError('Signature has expired')
jwt.exceptions.ExpiredSignatureError: Signature has expired
It is raising the exception and I imagine it is calling the Signature expired callback which sends the json back out but clearly something goes wrong and it bubbles up and Flask hands out a 500 in place of what would have been a signature expired json message as the flask dev server does.
This probably has nothing to do with this specific library at all and any hints at all your give me about which direction to go in on this would be much appreciated by me. Using this with the flask development server has been perfect but now getting something ready for production I am encountering this persistent issue. My regular views return json just fine with the production setup but these exceptions don't. I was hoping maybe somebody had been running this in production and would be able to give me a hint on where I went wrong here. Thanks!