Skip to content

Commit

Permalink
Merge branch 'refs/heads/main' into fix/credential-search-performance
Browse files Browse the repository at this point in the history
  • Loading branch information
byewokko committed Jun 27, 2024
2 parents 88551f4 + 8a4dbbd commit 49f4913
Show file tree
Hide file tree
Showing 4 changed files with 47 additions and 5 deletions.
6 changes: 6 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,9 @@
## v24.20

### Pre-releases
- `v24.20-alpha12`
- `v24.20-alpha11`
- `v24.20-alpha10`
- `v24.20-alpha9`
- `v24.20-alpha8`
- `v24.20-alpha7`
Expand All @@ -18,6 +21,8 @@
- Default password criteria are more restrictive (#372, `v24.20-alpha1`, Compatible with Seacat Auth Webui v24.19-alpha and later, Seacat Account Webui v24.08-beta and later)

### Fix
- Fix AttributeError in credentials update (#399, `v24.20-alpha11`)
- Catch token decoding errors when finding sessions (#397, `v24.20-alpha10`)
- Properly encrypt cookie value in session update (#394, `v24.20-alpha8`)
- Properly parse URL query before adding new parameters (#393, `v24.20-alpha8`)
- Delete client cookie on introspection failure (#385, `v24.20-alpha6`)
Expand All @@ -26,6 +31,7 @@
- Properly handle Argon2 verification error in login call (#378, `v24.20-alpha3`)

### Features
- Log login factor verification failure (#402, `v24.20-alpha12`)
- External login with dynamic redirection (#384, `v24.20-alpha9`)
- Custom response codes for tenant-related authorization errors (#392, `v24.20-alpha8`)
- Implement OAuth refresh tokens (#358, `v24.20-alpha2`)
Expand Down
6 changes: 6 additions & 0 deletions seacatauth/authn/login_descriptor.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import logging
import typing
import asab

from .login_factors import LoginFactorABC

Expand Down Expand Up @@ -101,6 +102,11 @@ async def authenticate(self, login_session, request_data):
assert len(self.FactorGroups) == 1
for factor in self.FactorGroups[0]:
if (await factor.authenticate(login_session, request_data)) is False:
L.log(asab.LOG_NOTICE, "Login factor verification failed.", struct_data={
"descriptor_id": self.ID,
"factor_type": factor.Type,
"cid": login_session.CredentialsId,
})
return False
return True

Expand Down
3 changes: 2 additions & 1 deletion seacatauth/credentials/service.py
Original file line number Diff line number Diff line change
Expand Up @@ -628,14 +628,15 @@ async def can_access_credentials(self, session, credentials_id: str) -> bool:
"""
Check if the target user is a member of currently authorized tenant
"""
tenant_service = self.App.get_service("seacatauth.TenantService")
if not session:
return False
if session.is_superuser():
return True
for tenant_id in session.Authorization.Authz.keys():
if tenant_id == "*":
continue
if await self.TenantService.has_tenant_assigned(credentials_id, tenant_id):
if await tenant_service.has_tenant_assigned(credentials_id, tenant_id):
# User is member of currently authorized tenant
return True
# The request and the target credentials have no tenant in common
Expand Down
37 changes: 33 additions & 4 deletions seacatauth/openidconnect/service.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import binascii
import datetime
import json
import base64
Expand Down Expand Up @@ -524,7 +525,15 @@ async def get_session_by_authorization_code(self, code, code_verifier: str | Non
"""
Retrieve session by its temporary authorization code.
"""
token_bytes = base64.urlsafe_b64decode(code.encode("ascii"))
try:
token_bytes = base64.urlsafe_b64decode(code.encode("ascii"))
except binascii.Error as e:
L.error("Corrupt authorization code format: Base64 decoding failed.", struct_data={"code": code})
raise exceptions.SessionNotFoundError("Corrupt authorization code format") from e
except UnicodeEncodeError as e:
L.error("Corrupt authorization code format: ASCII decoding failed.", struct_data={"code": code})
raise exceptions.SessionNotFoundError("Corrupt authorization code format") from e

token_data = await self.TokenService.get(token_bytes, token_type=AuthorizationCode.TokenType)
if "cc" in token_data:
self.PKCE.evaluate_code_challenge(
Expand All @@ -544,7 +553,17 @@ async def get_session_by_access_token(self, token_value: str):
"""
Retrieve session by its access token.
"""
token_bytes = base64.urlsafe_b64decode(token_value.encode("ascii"))
try:
token_bytes = base64.urlsafe_b64decode(token_value.encode("ascii"))
except binascii.Error as e:
L.error("Corrupt access token format: Base64 decoding failed.", struct_data={
"token_value": token_value})
raise exceptions.SessionNotFoundError("Corrupt access token format") from e
except UnicodeEncodeError as e:
L.error("Corrupt access token format: ASCII decoding failed.", struct_data={
"token_value": token_value})
raise exceptions.SessionNotFoundError("Corrupt access token format") from e

try:
token_data = await self.TokenService.get(token_bytes, token_type=AccessToken.TokenType)
except KeyError:
Expand All @@ -564,11 +583,21 @@ async def get_session_by_refresh_token(self, token_value: str):
"""
Retrieve session by its refresh token.
"""
token_bytes = base64.urlsafe_b64decode(token_value.encode("ascii"))
try:
token_bytes = base64.urlsafe_b64decode(token_value.encode("ascii"))
except binascii.Error as e:
L.error("Corrupt refresh token format: Base64 decoding failed.", struct_data={
"token_value": token_value})
raise exceptions.SessionNotFoundError("Corrupt refresh token format") from e
except UnicodeEncodeError as e:
L.error("Corrupt refresh token format: ASCII decoding failed.", struct_data={
"token_value": token_value})
raise exceptions.SessionNotFoundError("Corrupt refresh token format") from e

try:
token_data = await self.TokenService.get(token_bytes, token_type=RefreshToken.TokenType)
except KeyError:
raise exceptions.SessionNotFoundError("Invalid or expired access token")
raise exceptions.SessionNotFoundError("Invalid or expired refresh token")
try:
session = await self.SessionService.get(token_data["sid"])
except KeyError:
Expand Down

0 comments on commit 49f4913

Please sign in to comment.