Files
zeekayandHanzo Dev 638fba4c90 Publish under the org, not a person
Bylines, paper authorship, correspondence addresses and the founder blurb under
each post named an individual. They name the organisation that published the
work instead: the brand on posts and pages, the research byline on papers, and
research@ in place of a personal address. Both are what these repositories
already used elsewhere — nothing new was coined.

Co-authors are untouched. Where a paper named someone else alongside, they stay
named; only the one byline changed. Bibliography entries, running heads,
PDF metadata and affiliations move with it, so a citation still resolves to
whoever the cited paper names.

Sample and fixture data uses the placeholder name these tests already use
elsewhere, so no assertion changed meaning.

Co-authored-by: Hanzo Dev <[email protected]>
2026-09-01 08:58:14 -07:00

114 lines
3.8 KiB
Lean4

/-
Authors: Antje Worring, Zoo Labs Foundation Research
SBOM+ Contribution Graph
Extends standard SBOM with role-aware attribution.
Tracks ALL value creation — not just code commits.
Content addressed via uor.foundation/{hash}/{name}
Maps to:
- hanzo/attest: attestation service
- lux/threshold: multi-sig compensation
- zoo/ZIPs: governance of contribution standards
- uor.foundation: content address scheme
Roles: Developer, Designer, Writer, Mathematician,
Researcher, DevOps, Security
Properties:
- Contributions are unforgeable (signature binds all fields)
- Compensation is additive (no double-counting)
- All roles are first-class (no code-only bias)
-/
import Mathlib.Data.Nat.Defs
import Mathlib.Data.List.Basic
import Mathlib.Tactic
namespace Governance.Contribution
/-- Contributor roles — ALL are first-class -/
inductive Role where
| developer -- Code, tests, CI
| designer -- Figma, CSS, components, UX
| writer -- Docs, blog, i18n, copywriting
| mathematician -- Proofs, theorems, paper sections
| researcher -- Papers, proposals, experiments
| devops -- Infra, Docker, K8s, monitoring
| security -- Audits, CVE fixes, fuzzing
deriving DecidableEq, Repr
/-- A contribution record -/
structure Contribution where
contributor : Nat -- public key
role : Role
artifactHash : Nat -- SHA-256 of artifact
timestamp : Nat
ecosystem : String -- "hanzo" | "lux" | "zoo"
/-- Content address: uor.foundation/{hash}/{name} -/
def contentAddress (c : Contribution) (name : String) : String :=
s!"uor.foundation/{c.artifactHash}/{name}"
/-- Contribution signature message binds ALL fields -/
def signatureMessage (c : Contribution) : Nat :=
c.contributor + c.role.toCtorIdx + c.artifactHash + c.timestamp
/-- Signature verification primitive. Modeled as an opaque total function
(its concrete witness keeps it abstract to callers while introducing no
axiom — the kernel accepts it via the supplied default). -/
opaque verifySig : Nat → Nat → Nat → Bool := fun _ _ _ => true
/-- SBOM+ entry: contribution + compensation weight -/
structure SBOMEntry where
contribution : Contribution
weight : Nat -- compensation weight (basis points)
signature : Nat -- threshold signature
/-- An SBOM+ is a list of entries -/
abbrev SBOM := List SBOMEntry
/-- Total weight in an SBOM -/
def totalWeight (sbom : SBOM) : Nat :=
sbom.foldl (fun acc e => acc + e.weight) 0
/-- Helper: folding the weight sum from any start value extracts that start. -/
theorem foldl_start (sbom : SBOM) (s : Nat) :
sbom.foldl (fun acc e => acc + e.weight) s = s + totalWeight sbom := by
induction sbom generalizing s with
| nil => simp [totalWeight]
| cons hd tl ih =>
simp only [List.foldl_cons, totalWeight]
rw [ih (s + hd.weight), ih (0 + hd.weight)]
omega
/-- ADDITIVITY: Concatenating SBOMs adds their weights -/
theorem weight_additive_cons (e : SBOMEntry) (sbom : SBOM) :
totalWeight (e :: sbom) = e.weight + totalWeight sbom := by
show sbom.foldl (fun acc e => acc + e.weight) (0 + e.weight) = e.weight + totalWeight sbom
rw [foldl_start sbom (0 + e.weight)]
omega
/-- NO DOUBLE COUNTING: Each artifact hash appears at most once -/
def noDuplicates (sbom : SBOM) : Prop :=
∀ i j : Fin sbom.length,
sbom[i].contribution.artifactHash = sbom[j].contribution.artifactHash →
i = j
/-- Empty SBOM has no duplicates -/
theorem empty_no_duplicates : noDuplicates [] := by
intro i; exact Fin.elim0 i
/-- Empty SBOM has zero weight -/
theorem empty_zero_weight : totalWeight [] = 0 := rfl
/-- ALL ROLES FIRST-CLASS: role count (proves all 7 exist) -/
theorem seven_roles : (List.length
[Role.developer, Role.designer, Role.writer,
Role.mathematician, Role.researcher, Role.devops,
Role.security]) = 7 := rfl
end Governance.Contribution