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 9b70075  Show list of components for validation errors
9b70075 is described below

commit 9b70075250b134e0fc07badd35e2018754ca980f
Author: Alastair McFarlane <[email protected]>
AuthorDate: Tue Dec 16 11:42:21 2025 +0000

    Show list of components for validation errors
---
 atr/get/sbom.py                | 23 +++++++++++++++++++----
 atr/sbom/models/conformance.py |  8 +++++---
 2 files changed, 24 insertions(+), 7 deletions(-)

diff --git a/atr/get/sbom.py b/atr/get/sbom.py
index c85d477..dc88b7e 100644
--- a/atr/get/sbom.py
+++ b/atr/get/sbom.py
@@ -160,11 +160,15 @@ def _extract_vulnerability_severity(vuln: dict[str, Any]) 
-> str:
 def _missing_table(block: htm.Block, items: 
list[sbom.models.conformance.Missing]) -> None:
     warning_rows = [
         htm.tr[
-            htm.td[kind.upper()],
+            htm.td[
+                kind.upper()
+                if len(components) == 0
+                else htm.details[htm.summary[kind.upper()], 
htm.div[_detail_table(components)]]
+            ],
             htm.td[prop],
             htm.td[str(count)],
         ]
-        for kind, prop, count in _missing_tally(items)
+        for kind, prop, count, components in _missing_tally(items)
     ]
     block.table(".table.table-sm.table-bordered.table-striped")[
         htm.thead[htm.tr[htm.th["Kind"], htm.th["Property"], htm.th["Count"]]],
@@ -172,13 +176,24 @@ def _missing_table(block: htm.Block, items: 
list[sbom.models.conformance.Missing
     ]
 
 
-def _missing_tally(items: list[sbom.models.conformance.Missing]) -> 
list[tuple[str, str, int]]:
+def _detail_table(components: list[str | None]):
+    return htm.table(".table.table-sm.table-bordered.table-striped")[
+        htm.tbody[[htm.tr[htm.td[comp.capitalize()]] for comp in components if 
comp is not None]],
+    ]
+
+
+def _missing_tally(items: list[sbom.models.conformance.Missing]) -> 
list[tuple[str, str, int, list[str | None]]]:
     counts: dict[tuple[str, str], int] = {}
+    components: dict[tuple[str, str], list[str | None]] = {}
     for item in items:
         key = (getattr(item, "kind", ""), getattr(getattr(item, "property", 
None), "name", ""))
         counts[key] = counts.get(key, 0) + 1
+        if key not in components:
+            components[key] = [str(item)]
+        elif item.kind == "missing_component_property":
+            components[key].append(str(item))
     return sorted(
-        [(kind, prop, count) for (kind, prop), count in counts.items()],
+        [(item, prop, count, components.get((item, prop), [])) for (item, 
prop), count in counts.items()],
         key=lambda kv: (kv[0], kv[1]),
     )
 
diff --git a/atr/sbom/models/conformance.py b/atr/sbom/models/conformance.py
index 2d14a04..bdce64a 100644
--- a/atr/sbom/models/conformance.py
+++ b/atr/sbom/models/conformance.py
@@ -61,9 +61,11 @@ class MissingComponentProperty(Strict):
     index: int | None = None
 
     def __str__(self) -> str:
-        if self.index is None:
-            return f"missing {self.property.name} in primary component"
-        return f"missing {self.property.name} in component {self.index}"
+        if self.index is None or self.component is None:
+            comp = "primary component"
+        else:
+            comp = self.component
+        return f"missing {self.property.name} in {comp}"
 
     @pydantic.field_validator("property", mode="before")
     @classmethod


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

Reply via email to