def __init__(self, oauth_validator, user_svc, domain): self.oauth_validator = oauth_validator auth_code_grant = AuthorizationCodeGrant(oauth_validator) jwt_auth_grant = JWTAuthorizationGrant(oauth_validator, user_svc, domain) refresh_grant = RefreshTokenGrant(oauth_validator) refresh_grant.custom_validators.pre_token.append(self.load_client_id_from_refresh_token) bearer = BearerToken(oauth_validator, token_generator=self.generate_access_token, expires_in=ACCESS_TOKEN_TTL, refresh_token_generator=self.generate_refresh_token, refresh_token_expires_in=REFRESH_TOKEN_TTL) AuthorizationEndpoint.__init__(self, default_response_type='code', response_types={'code': auth_code_grant}, default_token_type=bearer) TokenEndpoint.__init__(self, default_grant_type='authorization_code', grant_types={ 'authorization_code': auth_code_grant, 'refresh_token': refresh_grant, 'urn:ietf:params:oauth:grant-type:jwt-bearer': jwt_auth_grant, }, default_token_type=bearer) RevocationEndpoint.__init__(self, oauth_validator)
def __init__(self, oauth_validator, user_svc, domain): self.oauth_validator = oauth_validator auth_code_grant = AuthorizationCodeGrant(oauth_validator) jwt_auth_grant = JWTAuthorizationGrant(oauth_validator, user_svc, domain) refresh_grant = RefreshTokenGrant(oauth_validator) refresh_grant.custom_validators.pre_token.append( self.load_client_id_from_refresh_token) bearer = BearerToken( oauth_validator, token_generator=self.generate_access_token, expires_in=ACCESS_TOKEN_TTL, refresh_token_generator=self.generate_refresh_token, refresh_token_expires_in=REFRESH_TOKEN_TTL) AuthorizationEndpoint.__init__( self, default_response_type='code', response_types={'code': auth_code_grant}, default_token_type=bearer) TokenEndpoint.__init__( self, default_grant_type='authorization_code', grant_types={ 'authorization_code': auth_code_grant, 'refresh_token': refresh_grant, 'urn:ietf:params:oauth:grant-type:jwt-bearer': jwt_auth_grant, }, default_token_type=bearer) RevocationEndpoint.__init__(self, oauth_validator)
def setUp(self): self.validator = MagicMock(wraps=RequestValidator()) self.validator.authenticate_client.return_value = True self.validator.revoke_token.return_value = True self.endpoint = RevocationEndpoint(self.validator) self.uri = 'https://example.com/revoke_token' self.headers = { 'Content-Type': 'application/x-www-form-urlencoded', }
def test_revoke_with_callback(self): endpoint = RevocationEndpoint(self.validator, enable_jsonp=True) callback = 'package.hello_world' for token_type in ('access_token', 'refresh_token', 'invalid'): body = urlencode([('token', 'foo'), ('token_type_hint', token_type), ('callback', callback)]) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, callback + '();') self.assertEqual(s, 200)
class RevocationEndpointTest(TestCase): def setUp(self): self.validator = MagicMock(wraps=RequestValidator()) self.validator.authenticate_client.return_value = True self.validator.revoke_token.return_value = True self.endpoint = RevocationEndpoint(self.validator) self.uri = 'https://example.com/revoke_token' self.headers = { 'Content-Type': 'application/x-www-form-urlencoded', } def test_revoke_token(self): for token_type in ('access_token', 'refresh_token', 'invalid'): body = urlencode([('token', 'foo'), ('token_type_hint', token_type)]) h, b, s = self.endpoint.create_revocation_response( self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, None) self.assertEqual(s, 200) def test_revoke_with_callback(self): callback = 'package.hello_world' for token_type in ('access_token', 'refresh_token', 'invalid'): body = urlencode([('token', 'foo'), ('token_type_hint', token_type), ('callback', callback)]) h, b, s = self.endpoint.create_revocation_response( self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, callback + '()') self.assertEqual(s, 200) def test_revoke_unsupported_token(self): endpoint = RevocationEndpoint(self.validator, supported_token_types=['access_token']) body = urlencode([('token', 'foo'), ('token_type_hint', 'refresh_token')]) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(loads(b)['error'], 'unsupported_token_type') self.assertEqual(s, 400) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body='') self.assertEqual(h, {}) self.assertEqual(loads(b)['error'], 'invalid_request') self.assertEqual(s, 400)
def test_revoke_bad_post_request(self): endpoint = RevocationEndpoint(self.validator, supported_token_types=['access_token']) for param in ['token', 'secret', 'code', 'foo']: uri = 'http://some.endpoint?' + urlencode([(param, 'secret')]) body = urlencode([('token', 'foo'), ('token_type_hint', 'access_token')]) h, b, s = endpoint.create_revocation_response(uri, headers=self.headers, body=body) self.assertEqual(h, self.resp_h) self.assertEqual(loads(b)['error'], 'invalid_request') self.assertIn('query parameters are not allowed', loads(b)['error_description']) self.assertEqual(s, 400)
class RevocationEndpointTest(TestCase): def setUp(self): self.validator = MagicMock(wraps=RequestValidator()) self.validator.authenticate_client.return_value = True self.validator.revoke_token.return_value = True self.endpoint = RevocationEndpoint(self.validator) self.uri = 'https://example.com/revoke_token' self.headers = { 'Content-Type': 'application/x-www-form-urlencoded', } def test_revoke_token(self): for token_type in ('access_token', 'refresh_token', 'invalid'): body = urlencode([('token', 'foo'), ('token_type_hint', token_type)]) h, b, s = self.endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, None) self.assertEqual(s, 200) def test_revoke_with_callback(self): callback = 'package.hello_world' for token_type in ('access_token', 'refresh_token', 'invalid'): body = urlencode([('token', 'foo'), ('token_type_hint', token_type), ('callback', callback)]) h, b, s = self.endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, callback + '()') self.assertEqual(s, 200) def test_revoke_unsupported_token(self): endpoint = RevocationEndpoint(self.validator, supported_token_types=['access_token']) body = urlencode([('token', 'foo'), ('token_type_hint', 'refresh_token')]) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(loads(b)['error'], 'unsupported_token_type') self.assertEqual(s, 400) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body='') self.assertEqual(h, {}) self.assertEqual(loads(b)['error'], 'invalid_request') self.assertEqual(s, 400)
def test_revoke_invalid_request_method(self): endpoint = RevocationEndpoint(self.validator, supported_token_types=['access_token']) test_methods = ['GET', 'pUt', 'dEleTe', 'paTcH'] test_methods = test_methods + [x.lower() for x in test_methods] + [x.upper() for x in test_methods] for method in test_methods: body = urlencode([('token', 'foo'), ('token_type_hint', 'refresh_token')]) h, b, s = endpoint.create_revocation_response(self.uri, http_method = method, headers=self.headers, body=body) self.assertEqual(h, self.resp_h) self.assertEqual(loads(b)['error'], 'invalid_request') self.assertIn('Unsupported request method', loads(b)['error_description']) self.assertEqual(s, 400)
def __init__(self, request_validator, token_expires_in=None, token_generator=None, refresh_token_generator=None, *args, **kwargs): """Construct a new all-grants-in-one server. :param request_validator: An implementation of oauthlib.oauth2.RequestValidator. :param token_expires_in: An int or a function to generate a token expiration offset (in seconds) given a oauthlib.common.Request object. :param token_generator: A function to generate a token from a request. :param refresh_token_generator: A function to generate a token from a request for the refresh token. :param kwargs: Extra parameters to pass to authorization-, token-, resource-, and revocation-endpoint constructors. """ auth_grant = AuthorizationCodeGrant(request_validator) implicit_grant = ImplicitGrant(request_validator) password_grant = ResourceOwnerPasswordCredentialsGrant( request_validator) facebook_grant = FacebookGrant(request_validator) credentials_grant = ClientCredentialsGrant(request_validator) refresh_grant = RefreshTokenGrant(request_validator) bearer = BearerToken(request_validator, token_generator, token_expires_in, refresh_token_generator) AuthorizationEndpoint.__init__(self, default_response_type='code', response_types={ 'code': auth_grant, 'token': implicit_grant, }, default_token_type=bearer) TokenEndpoint.__init__(self, default_grant_type='authorization_code', grant_types={ 'authorization_code': auth_grant, 'password': password_grant, 'facebook': facebook_grant, 'client_credentials': credentials_grant, 'refresh_token': refresh_grant, }, default_token_type=bearer) ResourceEndpoint.__init__(self, default_token='Bearer', token_types={'Bearer': bearer}) RevocationEndpoint.__init__(self, request_validator)
def setUp(self): self.validator = MagicMock(wraps=RequestValidator()) self.validator.client_authentication_required.return_value = True self.validator.authenticate_client.return_value = True self.validator.revoke_token.return_value = True self.endpoint = RevocationEndpoint(self.validator) self.uri = 'https://example.com/revoke_token' self.headers = { 'Content-Type': 'application/x-www-form-urlencoded', } self.resp_h = { 'Cache-Control': 'no-store', 'Content-Type': 'application/json', 'Pragma': 'no-cache' }
def test_revoke_unsupported_token(self): endpoint = RevocationEndpoint(self.validator, supported_token_types=['access_token']) body = urlencode([('token', 'foo'), ('token_type_hint', 'refresh_token')]) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(loads(b)['error'], 'unsupported_token_type') self.assertEqual(s, 400) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body='') self.assertEqual(h, {}) self.assertEqual(loads(b)['error'], 'invalid_request') self.assertEqual(s, 400)
class RevocationEndpointTest(TestCase): def setUp(self): self.validator = MagicMock(wraps=RequestValidator()) self.validator.client_authentication_required.return_value = True self.validator.authenticate_client.return_value = True self.validator.revoke_token.return_value = True self.endpoint = RevocationEndpoint(self.validator) self.uri = 'https://example.com/revoke_token' self.headers = { 'Content-Type': 'application/x-www-form-urlencoded', } self.resp_h = { 'Cache-Control': 'no-store', 'Content-Type': 'application/json', 'Pragma': 'no-cache' } def test_revoke_token(self): for token_type in ('access_token', 'refresh_token', 'invalid'): body = urlencode([('token', 'foo'), ('token_type_hint', token_type)]) h, b, s = self.endpoint.create_revocation_response( self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, '') self.assertEqual(s, 200) # don't specify token_type_hint body = urlencode([('token', 'foo')]) h, b, s = self.endpoint.create_revocation_response( self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, '') self.assertEqual(s, 200) def test_revoke_token_client_authentication_failed(self): self.validator.authenticate_client.return_value = False body = urlencode([('token', 'foo'), ('token_type_hint', 'access_token')]) h, b, s = self.endpoint.create_revocation_response( self.uri, headers=self.headers, body=body) self.assertEqual( h, { 'Content-Type': 'application/json', 'Cache-Control': 'no-store', 'Pragma': 'no-cache', "WWW-Authenticate": 'Bearer, error="invalid_client"' }) self.assertEqual(loads(b)['error'], 'invalid_client') self.assertEqual(s, 401) def test_revoke_token_public_client_authentication(self): self.validator.client_authentication_required.return_value = False self.validator.authenticate_client_id.return_value = True for token_type in ('access_token', 'refresh_token', 'invalid'): body = urlencode([('token', 'foo'), ('token_type_hint', token_type)]) h, b, s = self.endpoint.create_revocation_response( self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, '') self.assertEqual(s, 200) def test_revoke_token_public_client_authentication_failed(self): self.validator.client_authentication_required.return_value = False self.validator.authenticate_client_id.return_value = False body = urlencode([('token', 'foo'), ('token_type_hint', 'access_token')]) h, b, s = self.endpoint.create_revocation_response( self.uri, headers=self.headers, body=body) self.assertEqual( h, { 'Content-Type': 'application/json', 'Cache-Control': 'no-store', 'Pragma': 'no-cache', "WWW-Authenticate": 'Bearer, error="invalid_client"' }) self.assertEqual(loads(b)['error'], 'invalid_client') self.assertEqual(s, 401) def test_revoke_with_callback(self): endpoint = RevocationEndpoint(self.validator, enable_jsonp=True) callback = 'package.hello_world' for token_type in ('access_token', 'refresh_token', 'invalid'): body = urlencode([('token', 'foo'), ('token_type_hint', token_type), ('callback', callback)]) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, callback + '();') self.assertEqual(s, 200) def test_revoke_unsupported_token(self): endpoint = RevocationEndpoint(self.validator, supported_token_types=['access_token']) body = urlencode([('token', 'foo'), ('token_type_hint', 'refresh_token')]) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, self.resp_h) self.assertEqual(loads(b)['error'], 'unsupported_token_type') self.assertEqual(s, 400) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body='') self.assertEqual(h, self.resp_h) self.assertEqual(loads(b)['error'], 'invalid_request') self.assertEqual(s, 400)
class RevocationEndpointTest(TestCase): def setUp(self): self.validator = MagicMock(wraps=RequestValidator()) self.validator.client_authentication_required.return_value = True self.validator.authenticate_client.return_value = True self.validator.revoke_token.return_value = True self.endpoint = RevocationEndpoint(self.validator) self.uri = 'https://example.com/revoke_token' self.headers = { 'Content-Type': 'application/x-www-form-urlencoded', } self.resp_h = { 'Cache-Control': 'no-store', 'Content-Type': 'application/json', 'Pragma': 'no-cache' } def test_revoke_token(self): for token_type in ('access_token', 'refresh_token', 'invalid'): body = urlencode([('token', 'foo'), ('token_type_hint', token_type)]) h, b, s = self.endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, '') self.assertEqual(s, 200) # don't specify token_type_hint body = urlencode([('token', 'foo')]) h, b, s = self.endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, '') self.assertEqual(s, 200) def test_revoke_token_client_authentication_failed(self): self.validator.authenticate_client.return_value = False body = urlencode([('token', 'foo'), ('token_type_hint', 'access_token')]) h, b, s = self.endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, { 'Content-Type': 'application/json', 'Cache-Control': 'no-store', 'Pragma': 'no-cache', "WWW-Authenticate": 'Bearer, error="invalid_client"' }) self.assertEqual(loads(b)['error'], 'invalid_client') self.assertEqual(s, 401) def test_revoke_token_public_client_authentication(self): self.validator.client_authentication_required.return_value = False self.validator.authenticate_client_id.return_value = True for token_type in ('access_token', 'refresh_token', 'invalid'): body = urlencode([('token', 'foo'), ('token_type_hint', token_type)]) h, b, s = self.endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, '') self.assertEqual(s, 200) def test_revoke_token_public_client_authentication_failed(self): self.validator.client_authentication_required.return_value = False self.validator.authenticate_client_id.return_value = False body = urlencode([('token', 'foo'), ('token_type_hint', 'access_token')]) h, b, s = self.endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, { 'Content-Type': 'application/json', 'Cache-Control': 'no-store', 'Pragma': 'no-cache', "WWW-Authenticate": 'Bearer, error="invalid_client"' }) self.assertEqual(loads(b)['error'], 'invalid_client') self.assertEqual(s, 401) def test_revoke_with_callback(self): endpoint = RevocationEndpoint(self.validator, enable_jsonp=True) callback = 'package.hello_world' for token_type in ('access_token', 'refresh_token', 'invalid'): body = urlencode([('token', 'foo'), ('token_type_hint', token_type), ('callback', callback)]) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, callback + '();') self.assertEqual(s, 200) def test_revoke_unsupported_token(self): endpoint = RevocationEndpoint(self.validator, supported_token_types=['access_token']) body = urlencode([('token', 'foo'), ('token_type_hint', 'refresh_token')]) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, self.resp_h) self.assertEqual(loads(b)['error'], 'unsupported_token_type') self.assertEqual(s, 400) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body='') self.assertEqual(h, self.resp_h) self.assertEqual(loads(b)['error'], 'invalid_request') self.assertEqual(s, 400)
def __init__(self, request_validator, token_expires_in=None, token_generator=None, refresh_token_generator=None, *args, **kwargs): """Construct a new all-grants-in-one server. :param request_validator: An implementation of oauthlib.oauth2.RequestValidator. :param token_expires_in: An int or a function to generate a token expiration offset (in seconds) given a oauthlib.common.Request object. :param token_generator: A function to generate a token from a request. :param refresh_token_generator: A function to generate a token from a request for the refresh token. :param kwargs: Extra parameters to pass to authorization-, token-, resource-, and revocation-endpoint constructors. """ auth_grant = AuthorizationCodeGrant(request_validator) implicit_grant = ImplicitGrant(request_validator) password_grant = ResourceOwnerPasswordCredentialsGrant( request_validator) credentials_grant = ClientCredentialsGrant(request_validator) refresh_grant = RefreshTokenGrant(request_validator) openid_connect_auth = OpenIDConnectAuthCode(request_validator) openid_connect_implicit = OpenIDConnectImplicit(request_validator) bearer = BearerToken(request_validator, token_generator, token_expires_in, refresh_token_generator) auth_grant_choice = AuthCodeGrantDispatcher( default_auth_grant=auth_grant, oidc_auth_grant=openid_connect_auth) # See http://openid.net/specs/oauth-v2-multiple-response-types-1_0.html#Combinations for valid combinations # noqa # internally our AuthorizationEndpoint will ensure they can appear in any order for any valid combination # noqa AuthorizationEndpoint.__init__( self, default_response_type='code', response_types={ 'code': auth_grant_choice, 'token': implicit_grant, 'id_token': openid_connect_implicit, 'id_token token': openid_connect_implicit, 'code token': openid_connect_auth, 'code id_token': openid_connect_auth, 'code token id_token': openid_connect_auth, 'none': auth_grant }, default_token_type=bearer) TokenEndpoint.__init__( self, default_grant_type='authorization_code', grant_types={ 'authorization_code': openid_connect_auth, 'password': password_grant, 'client_credentials': credentials_grant, 'refresh_token': refresh_grant, 'openid': openid_connect_auth }, default_token_type=bearer) ResourceEndpoint.__init__( self, default_token='Bearer', token_types={'Bearer': bearer}) RevocationEndpoint.__init__(self, request_validator)
class RevocationEndpointTest(TestCase): def setUp(self): self.validator = MagicMock(wraps=RequestValidator()) self.validator.client_authentication_required.return_value = True self.validator.authenticate_client.return_value = True self.validator.revoke_token.return_value = True self.endpoint = RevocationEndpoint(self.validator) self.uri = 'https://example.com/revoke_token' self.headers = { 'Content-Type': 'application/x-www-form-urlencoded', } self.resp_h = { 'Cache-Control': 'no-store', 'Content-Type': 'application/json', 'Pragma': 'no-cache' } def test_revoke_token(self): for token_type in ('access_token', 'refresh_token', 'invalid'): body = urlencode([('token', 'foo'), ('token_type_hint', token_type)]) h, b, s = self.endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, '') self.assertEqual(s, 200) # don't specify token_type_hint body = urlencode([('token', 'foo')]) h, b, s = self.endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, '') self.assertEqual(s, 200) def test_revoke_token_client_authentication_failed(self): self.validator.authenticate_client.return_value = False body = urlencode([('token', 'foo'), ('token_type_hint', 'access_token')]) h, b, s = self.endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, { 'Content-Type': 'application/json', 'Cache-Control': 'no-store', 'Pragma': 'no-cache', "WWW-Authenticate": 'Bearer, error="invalid_client"' }) self.assertEqual(loads(b)['error'], 'invalid_client') self.assertEqual(s, 401) def test_revoke_token_public_client_authentication(self): self.validator.client_authentication_required.return_value = False self.validator.authenticate_client_id.return_value = True for token_type in ('access_token', 'refresh_token', 'invalid'): body = urlencode([('token', 'foo'), ('token_type_hint', token_type)]) h, b, s = self.endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, '') self.assertEqual(s, 200) def test_revoke_token_public_client_authentication_failed(self): self.validator.client_authentication_required.return_value = False self.validator.authenticate_client_id.return_value = False body = urlencode([('token', 'foo'), ('token_type_hint', 'access_token')]) h, b, s = self.endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, { 'Content-Type': 'application/json', 'Cache-Control': 'no-store', 'Pragma': 'no-cache', "WWW-Authenticate": 'Bearer, error="invalid_client"' }) self.assertEqual(loads(b)['error'], 'invalid_client') self.assertEqual(s, 401) def test_revoke_with_callback(self): endpoint = RevocationEndpoint(self.validator, enable_jsonp=True) callback = 'package.hello_world' for token_type in ('access_token', 'refresh_token', 'invalid'): body = urlencode([('token', 'foo'), ('token_type_hint', token_type), ('callback', callback)]) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, {}) self.assertEqual(b, callback + '();') self.assertEqual(s, 200) def test_revoke_unsupported_token(self): endpoint = RevocationEndpoint(self.validator, supported_token_types=['access_token']) body = urlencode([('token', 'foo'), ('token_type_hint', 'refresh_token')]) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body=body) self.assertEqual(h, self.resp_h) self.assertEqual(loads(b)['error'], 'unsupported_token_type') self.assertEqual(s, 400) h, b, s = endpoint.create_revocation_response(self.uri, headers=self.headers, body='') self.assertEqual(h, self.resp_h) self.assertEqual(loads(b)['error'], 'invalid_request') self.assertEqual(s, 400) def test_revoke_invalid_request_method(self): endpoint = RevocationEndpoint(self.validator, supported_token_types=['access_token']) test_methods = ['GET', 'pUt', 'dEleTe', 'paTcH'] test_methods = test_methods + [x.lower() for x in test_methods] + [x.upper() for x in test_methods] for method in test_methods: body = urlencode([('token', 'foo'), ('token_type_hint', 'refresh_token')]) h, b, s = endpoint.create_revocation_response(self.uri, http_method = method, headers=self.headers, body=body) self.assertEqual(h, self.resp_h) self.assertEqual(loads(b)['error'], 'invalid_request') self.assertIn('Unsupported request method', loads(b)['error_description']) self.assertEqual(s, 400) def test_revoke_bad_post_request(self): endpoint = RevocationEndpoint(self.validator, supported_token_types=['access_token']) for param in ['token', 'secret', 'code', 'foo']: uri = 'http://some.endpoint?' + urlencode([(param, 'secret')]) body = urlencode([('token', 'foo'), ('token_type_hint', 'access_token')]) h, b, s = endpoint.create_revocation_response(uri, headers=self.headers, body=body) self.assertEqual(h, self.resp_h) self.assertEqual(loads(b)['error'], 'invalid_request') self.assertIn('query parameters are not allowed', loads(b)['error_description']) self.assertEqual(s, 400)