Аргумент query_client отсутствует в AuthorizationServer
Я определил query_client
в ленивой инициализации моего AuthorizationServer
как сказано здесь, но это не работает: query_client
является None
еще.
Вот мой модуль oauth:
from authlib.common.security import generate_token
from authlib.flask.oauth2 import AuthorizationServer, ResourceProtector
from authlib.flask.oauth2.sqla import create_revocation_endpoint, create_bearer_token_validator
from authlib.specs.rfc6749 import grants, OAuth2Token
from flask import session
from website.models import Client, Token, db, User, AuthorizationCode
server = AuthorizationServer()
require_oauth = ResourceProtector()
class AuthorizationCodeGrant(grants.AuthorizationCodeGrant):
def create_authorization_code(self, client, grant_user, request):
# you can use other method to generate this code
code = generate_token(48)
item = AuthorizationCode(
code=code,
client_id=client.client_id,
redirect_uri=request.redirect_uri,
scope=request.scope,
user_id=grant_user.get_user_id(),
)
db.session.add(item)
db.session.commit()
return code
def parse_authorization_code(self, code, client):
item = AuthorizationCode.query.filter_by(code=code, client_id=client.client_id)\
.first()
if item and not item.is_expired():
return item
def delete_authorization_code(self, authorization_code):
db.session.delete(authorization_code)
db.session.commit()
def authenticate_user(self, authorization_code):
return User.query.get(authorization_code.user_id)
class PasswordGrant(grants.ResourceOwnerPasswordCredentialsGrant):
def authenticate_user(self, email, password):
user = User.query.filter_by(email=email).first()
if user.check_password(password):
return user
class RefreshTokenGrant(grants.RefreshTokenGrant):
def authenticate_refresh_token(self, refresh_token):
item = OAuth2Token.query.filter_by(refresh_token=refresh_token).first()
if item and not item.is_refresh_token_expired():
return item
def authenticate_user(self, credential):
return User.query.get(credential.user_id)
def current_user():
if 'id' in session:
uid = session['id']
return User.query.get(uid)
return None
def query_client(client_id):
return Client.query.filter_by(client_id=client_id).first()
def save_token(token, request):
if request.user:
user_id = request.user.get_user_id()
else:
# client_credentials grant_type
user_id = request.client.user_id
item = Token(
client_id=request.client.client_id,
user_id=user_id,
**token
)
db.session.add(item)
db.session.commit()
def init_oauth2(app):
server.init_app(app, query_client=query_client, save_token=save_token)
# register it to grant endpoint
server.register_grant(grants.ImplicitGrant)
server.register_grant(AuthorizationCodeGrant)
server.register_grant(grants.ClientCredentialsGrant)
server.register_grant(PasswordGrant)
server.register_grant(RefreshTokenGrant)
# support revocation
revocation_cls = create_revocation_endpoint(db.session, OAuth2Token)
server.register_endpoint(revocation_cls)
# protect resource
bearer_cls = create_bearer_token_validator(db.session, OAuth2Token)
require_oauth.register_token_validator(bearer_cls())
По запросу oauth/token
Я получаю ошибку:
Traceback (most recent call last):
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/flask/app.py", line 2309, in __call__
return self.wsgi_app(environ, start_response)
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/flask/app.py", line 2295, in wsgi_app
response = self.handle_exception(e)
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/flask_restful/__init__.py", line 273, in error_router
return original_handler(e)
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/flask/app.py", line 1741, in handle_exception
reraise(exc_type, exc_value, tb)
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/flask/_compat.py", line 35, in reraise
raise value
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/flask/app.py", line 2292, in wsgi_app
response = self.full_dispatch_request()
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/flask/app.py", line 1815, in full_dispatch_request
rv = self.handle_user_exception(e)
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/flask_restful/__init__.py", line 273, in error_router
return original_handler(e)
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/flask/app.py", line 1718, in handle_user_exception
reraise(exc_type, exc_value, tb)
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/flask/_compat.py", line 35, in reraise
raise value
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/flask/app.py", line 1813, in full_dispatch_request
rv = self.dispatch_request()
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/flask/app.py", line 1799, in dispatch_request
return self.view_functions[rule.endpoint](**req.view_args)
File "/home/ghostman/Projects/vistory/auth/website/routes.py", line 124, in issue_token
return server.create_token_response()
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/authlib/flask/oauth2/authorization_server.py", line 251, in create_token_response
AuthorizationServer, self).create_token_response(req)
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/authlib/specs/rfc6749/authorization_server.py", line 162, in create_token_response
grant.validate_token_request()
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/authlib/specs/rfc6749/grants/authorization_code.py", line 233, in validate_token_request
client = self.authenticate_token_endpoint_client()
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/authlib/specs/rfc6749/grants/base.py", line 76, in authenticate_token_endpoint_client
self.TOKEN_ENDPOINT_AUTH_METHODS
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/authlib/specs/rfc6749/authenticate_client.py", line 51, in __call__
return self.authenticate(request, methods)
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/authlib/specs/rfc6749/authenticate_client.py", line 42, in authenticate
client = func(self.query_client, request)
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/authlib/specs/rfc6749/authenticate_client.py", line 60, in authenticate_client_secret_basic
client = _validate_client(query_client, client_id, request.state, 401)
File "/home/ghostman/Projects/vistory/auth/venv/lib/python3.6/site-packages/authlib/specs/rfc6749/authenticate_client.py", line 120, in _validate_client
client = query_client(client_id)
TypeError: 'NoneType' object is not callable
Я проверил в отладчике query_client=None
даже после ленивой инициализации.
Что я делаю неправильно?
ДОБАВЛЕНО:
Маршрут должен получить токен:
@bp.route('/oauth/token', methods=['POST'])
def issue_token():
return server.create_token_response()