You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@tooling.apache.org by ar...@apache.org on 2026/08/07 10:53:26 UTC

(tooling-trusted-releases) branch arm updated: #1420 - highlight revoked keys

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

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


The following commit(s) were added to refs/heads/arm by this push:
     new e43f2919 #1420 - highlight revoked keys
e43f2919 is described below

commit e43f2919bf4f162252eb91a6696961b16c58cdc2
Author: Alastair McFarlane <ar...@apache.org>
AuthorDate: Fri Aug 7 11:53:01 2026 +0100

    #1420 - highlight revoked keys
---
 atr/db/__init__.py | 10 +++++++++-
 atr/get/keys.py    | 28 +++++++++++++++++++++-------
 2 files changed, 30 insertions(+), 8 deletions(-)

diff --git a/atr/db/__init__.py b/atr/db/__init__.py
index fbfce06b..04e2deb6 100644
--- a/atr/db/__init__.py
+++ b/atr/db/__init__.py
@@ -350,6 +350,7 @@ class Session(sqlalchemy.ext.asyncio.AsyncSession):
         _child_committees: bool = False,
         _projects: bool = False,
         _signing_certificates: bool = False,
+        _signing_keys: bool = False,
     ) -> Query[sql.Committee]:
         via = sql.validate_instrumented_attribute
         query = sqlmodel.select(sql.Committee)
@@ -387,7 +388,11 @@ class Session(sqlalchemy.ext.asyncio.AsyncSession):
             query = query.options(select_in_load(sql.Committee.child_committees))
         if _projects:
             query = query.options(select_in_load(sql.Committee.projects))
-        if _signing_certificates:
+        if _signing_certificates and _signing_keys:
+            query = query.options(
+                select_in_load_nested(sql.Committee.signing_certificates, sql.SigningCertificate.signing_keys)
+            )
+        elif _signing_certificates:
             query = query.options(select_in_load(sql.Committee.signing_certificates))
 
         return Query(self, query)
@@ -592,6 +597,7 @@ class Session(sqlalchemy.ext.asyncio.AsyncSession):
         deleted: Opt[bool] = False,
         historic_use: Opt[bool] = NOT_SET,
         _committees: bool = False,
+        _signing_keys: bool = False,
     ) -> Query[sql.SigningCertificate]:
         via = sql.validate_instrumented_attribute
         query = sqlmodel.select(sql.SigningCertificate)
@@ -616,6 +622,8 @@ class Session(sqlalchemy.ext.asyncio.AsyncSession):
 
         if _committees:
             query = query.options(select_in_load(sql.SigningCertificate.committees))
+        if _signing_keys:
+            query = query.options(select_in_load(sql.SigningCertificate.signing_keys))
 
         return Query(self, query)
 
diff --git a/atr/get/keys.py b/atr/get/keys.py
index d929e31b..f94e7be4 100644
--- a/atr/get/keys.py
+++ b/atr/get/keys.py
@@ -228,9 +228,13 @@ async def keys(session: web.Committer, _keys: Literal["keys"]) -> str:
     committees_to_query = list(set(session.member_committees + session.participant_committees))
 
     async with db.session() as data:
-        user_keys = await data.signing_certificate(apache_uid=session.uid.lower(), _committees=True).all()
+        user_keys = await data.signing_certificate(
+            apache_uid=session.uid.lower(), _committees=True, _signing_keys=True
+        ).all()
         user_ssh_keys = await data.ssh_key(asf_uid=session.uid).all()
-        user_committees_with_keys = await data.committee(name_in=committees_to_query, _signing_certificates=True).all()
+        user_committees_with_keys = await data.committee(
+            name_in=committees_to_query, _signing_certificates=True, _signing_keys=True
+        ).all()
 
         all_fingerprints = [k.fingerprint for c in user_committees_with_keys for k in c.signing_certificates]
         artifact_counts: dict[str, int] = {}
@@ -347,6 +351,19 @@ def _add_signing_keys(page: htm.Block, signing_keys: list[sql.SigningKey]) -> No
     page.div(".table-responsive.mb-4")[htm.table(".table.border.table-striped.table-sm")[thead, tbody.collect()]]
 
 
+def _certificate_key_id(key: sql.SigningCertificate) -> htm.Element:
+    link = htm.a(href=util.as_url(details, fingerprint=key.fingerprint))[key.fingerprint[-16:].upper()]
+    # A certificate whose primary and every subkey are revoked can't sign anything, so strike it through
+    # and say so, since these tables carry no per-key status column
+    if key.signing_keys and all(signing_key.revoked for signing_key in key.signing_keys):
+        return htm.span[
+            htm.span(".text-decoration-line-through")[link],
+            " ",
+            htm.span(".text-muted")["(revoked)"],
+        ]
+    return link
+
+
 async def _committee_keys(
     page: htm.Block,
     user_committees_with_keys: list[sql.Committee],
@@ -377,8 +394,7 @@ async def _committee_keys(
                 tbody = htm.Block(htm.tbody)
                 for key in sorted_keys:
                     row = htm.Block(htm.tr)
-                    details_url = util.as_url(details, fingerprint=key.fingerprint)
-                    row.td(".text-break.font-monospace.px-2")[htm.a(href=details_url)[key.fingerprint[-16:].upper()]]
+                    row.td(".text-break.font-monospace.px-2")[_certificate_key_id(key)]
                     email = util.email_from_uid(key.primary_declared_uid) if key.primary_declared_uid else "-"
                     row.td(".text-break.px-2")[email or "-"]
                     row.td(".text-break.px-2")[key.apache_uid or "-"]
@@ -462,9 +478,7 @@ async def _openpgp_keys(page: htm.Block, user_keys: list[sql.SigningCertificate]
         tbody = htm.Block(htm.tbody)
         for key in user_keys:
             row = htm.Block(htm.tr, classes=".page-user-openpgp-key")
-            row.td(".text-break.px-2.align-middle")[
-                htm.a(href=util.as_url(details, fingerprint=key.fingerprint))[key.fingerprint[-16:].upper()]
-            ]
+            row.td(".text-break.px-2.align-middle")[_certificate_key_id(key)]
             if key.committees:
                 committee_keys = ", ".join([c.key for c in key.committees])
                 row.td(".text-break.px-2.align-middle")[committee_keys]


---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@tooling.apache.org
For additional commands, e-mail: commits-help@tooling.apache.org