# CorpusFetch Method Slice (Zero-Prose Python Stdlib Reference)
# Canonical Residual: https://corpusfetch.com/c/where-must-an-instance-of-the-a2a-agent-card-discovery-trust-boundary-be-enforced-when-a-delegated-task-crosses-a-vendor-signing-boundary.md
# Remnant Warrant:    https://corpusfetch.com/c/where-must-an-instance-of-the-a2a-agent-card-discovery-trust-boundary-be-enforced-when-a-delegated-task-crosses-a-vendor-signing-boundary.warrant.json
# Markdown SHA-256:   3d661df760820bfebf204541a9fae7f9733b899a5a5077d760714b6fbcc8efb3
# Code AST SHA-256:   7c9f3349bd51dccee7e52564507c2f6fef3b9e67d3ae3f2f76a39e14991b30ef
# Verified Classes:   ArtifactVerificationError, AgentCard, Artifact
# Defensive Guards:   6 fail-closed invariants (zero external deps)

from dataclasses import dataclass
from typing import Optional


class ArtifactVerificationError(RuntimeError):
    """Raised when an A2A artifact cannot be bound to a trusted signing identity."""
    pass


@dataclass
class AgentCard:
    url: str                    # transport identity, e.g. "https://research.vendor-b.example"
    signing_issuer: str         # declared artifact signing issuer
    delegation_chain: list      # cert chain terminating at a configured trust root
    key_id: str


@dataclass
class Artifact:
    key_id: str
    signature: bytes
    payload: bytes
    created_at: float


def verify_artifact(
    card: AgentCard,
    artifact: Artifact,
    trust_roots: set[str],
    now: float,
) -> None:
    # 1. The artifact must be signed by the key the card declared, not the transport host.
    if artifact.key_id != card.key_id:
        raise ArtifactVerificationError(
            f"artifact key_id {artifact.key_id!r} does not match card-declared "
            f"{card.key_id!r}; transport host {card.url!r} is not a signing identity"
        )

    # 2. Walk the delegation chain to a configured trust root. Do not trust `issuer` verbatim.
    chain = card.delegation_chain
    if not chain:
        raise ArtifactVerificationError(
            f"card {card.url!r} declares issuer {card.signing_issuer!r} but supplies no "
            f"delegation chain; cannot bind artifact to a trust root"
        )
    root = chain[-1].issuer
    if root not in trust_roots:
        raise ArtifactVerificationError(
            f"delegation chain for {card.key_id!r} terminates at {root!r}, "
            f"which is not in the configured trust store"
        )
    for link in chain:
        if not link.valid_at(now):
            raise ArtifactVerificationError(
                f"delegation link {link.subject!r} not valid at artifact time {now}"
            )
        if "digitalSignature" not in link.key_usage:
            raise ArtifactVerificationError(
                f"delegation link {link.subject!r} lacks digitalSignature keyUsage"
            )

    # 3. Only now is the signature meaningful; verify over the declared key.
    if not artifact.signature.verify(artifact.payload, card.key_id):
        raise ArtifactVerificationError(
            f"signature verification failed for artifact under {card.key_id!r}"
        )


def accept_task_completed(card: AgentCard, artifacts: list[Artifact],
                          trust_roots: set[str], now: float) -> None:
    # `completed` is terminal ONLY after every artifact passes the gate above.
    for art in artifacts:
        verify_artifact(card, art, trust_roots, now)
