This is an automated email from the ASF dual-hosted git repository.

arm pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/tooling-trusted-releases.git


The following commit(s) were added to refs/heads/main by this push:
     new 1699697  #598 - Check for account existence before issuing JWT
1699697 is described below

commit 169969746b3a0a8bad6b0215317ad25b50eee473
Author: Alastair McFarlane <[email protected]>
AuthorDate: Wed Jan 28 11:16:59 2026 +0000

    #598 - Check for account existence before issuing JWT
---
 atr/ldap.py                   | 25 +++++++++++++++++++++++++
 atr/storage/writers/tokens.py |  7 +++++++
 2 files changed, 32 insertions(+)

diff --git a/atr/ldap.py b/atr/ldap.py
index 8cc429d..f374246 100644
--- a/atr/ldap.py
+++ b/atr/ldap.py
@@ -97,6 +97,31 @@ class SearchParameters:
     email_only: bool = False
 
 
+async def account_lookup(asf_uid: str) -> dict[str, str | list[str]] | None:
+    """
+    Look up an account in LDAP by ASF UID.
+
+    Returns the account details dict if found, None if the account does not 
exist.
+    If LDAP is not configured, returns None to avoid breaking functionality.
+    """
+    credentials = get_bind_credentials()
+    if credentials is None:
+        return None
+
+    bind_dn, bind_password = credentials
+    params = SearchParameters(
+        uid_query=asf_uid,
+        bind_dn_from_config=bind_dn,
+        bind_password_from_config=bind_password,
+    )
+    await asyncio.to_thread(search, params)
+
+    if not params.results_list:
+        return None
+
+    return params.results_list[0]
+
+
 async def fetch_admin_users() -> frozenset[str]:
     import atr.log as log
 
diff --git a/atr/storage/writers/tokens.py b/atr/storage/writers/tokens.py
index 0877112..c72cd8e 100644
--- a/atr/storage/writers/tokens.py
+++ b/atr/storage/writers/tokens.py
@@ -26,6 +26,7 @@ import sqlmodel
 
 import atr.db as db
 import atr.jwtoken as jwtoken
+import atr.ldap as ldap
 import atr.mail as mail
 import atr.models.sql as sql
 import atr.storage as storage
@@ -116,6 +117,12 @@ class FoundationCommitter(GeneralPublic):
         )
         if (pat is None) or (pat.expires < 
datetime.datetime.now(datetime.UTC)):
             raise storage.AccessError("Authentication failed")
+
+        # Verify account still exists in LDAP
+        account_details = await ldap.account_lookup(self.__asf_uid)
+        if account_details is None:
+            raise storage.AccessError("Authentication failed")
+
         issued_jwt = jwtoken.issue(self.__asf_uid)
         pat.last_used = datetime.datetime.now(datetime.UTC)
         await self.__data.commit()


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to