Provenance badges are a UX problem
GitHub and npm can prove where artifacts came from. The harder design problem is making that proof useful before a developer installs the thing.
Provenance is only useful if it changes what someone does next.
GitHub's artifact attestations and npm's provenance statements are good infrastructure. They answer a question developers used to answer with vibes: where did this package or binary come from, and how was it built?
GitHub's docs say artifact attestations establish where and how software was built. A workflow can grant id-token: write, contents: read, and attestations: write, then call actions/attest@v4 after producing a binary or container image. npm's docs describe a similar chain for packages: provenance links a package to source code and build instructions, publish attestations are signed by Sigstore public-good servers, and the result lands in a public transparency ledger.
That is the backend doing its job.
The interface still has a much harder job: helping a tired developer decide whether to install, update, block, or investigate.
Sources: GitHub artifact attestation docs, GitHub artifact attestation concept docs, npm provenance docs, Sigstore overview.
A badge is not a decision
A provenance badge can easily become security theater.
The badge says, "this artifact has a receipt." It does not say the source is safe, the maintainer is trustworthy, the release is intentional, or the code is free of malicious behavior. npm is explicit about this. Its docs say provenance does not guarantee a package has no malicious code. It gives developers a verifiable link to source code and build instructions so they can audit and decide.
That caveat is correct. It is also where the UX work starts.
Most developers will not read an attestation statement before installing a transitive dependency. They will see a badge, a version number, a download count, and maybe a warning if the package manager gets loud enough. If the interface treats "has provenance" as the end of the story, users will learn the wrong lesson.
The useful design is not a green check. It is a small decision tree.
The install prompt should show the diff that matters
For a package update, I do not need a lecture about supply chain security. I need to know what changed about the release path.
A good package manager or registry UI should answer:
- Was the previous version attested?
- Did the workflow identity change?
- Did the repository URL change?
- Did the package publish method change from trusted publishing to token-based publishing?
- Does the attestation point to the same commit as the release tag?
Those are UX questions, not only security questions. They decide what belongs in the happy path and what deserves friction.
If a package has always published from the same GitHub Actions workflow and the new version matches that pattern, the interface can stay quiet. If the package suddenly publishes from a new repository, a new runner class, or a token-based path after months of trusted publishing, that should feel different. Not panic. Friction.
Verification needs a receipt view
GitHub documents gh attestation verify for binaries and container images. npm documents npm audit signatures to verify registry signatures and attestations. Those commands are useful for people who already know what they are checking.
The missing layer is a readable receipt view for normal development work.
I want a package page that says, in plain language:
This version was published from GitHub Actions. Repository: owner/project Workflow: release.yml Commit: abc123 Publisher: npm trusted publishing Changed since previous version: workflow file modified, dependency lockfile changed
Then give me the raw attestation if I need it.
That order matters. Raw proof is for audits. The default surface should explain the trust transition.
Security features need product taste
The awkward part is that provenance can be technically successful and still fail in practice.
If the UI makes every attested package look equally safe, users overtrust it. If it throws warnings for every small mismatch, users ignore it. The product has to decide which changes deserve attention.
That is where developer tools usually get uncomfortable. They would rather expose the primitive and let teams build policy around it. Fine for security teams. Weak for everyone else.
Provenance should become part of the everyday install experience. Quiet when the release path is consistent. Loud when the path changes in a way a maintainer would notice. Honest that a receipt is not a guarantee.
The infrastructure can prove origin. The interface has to teach consequence.