Contributing
Manual Curation Pipeline
The exact commands to take a skill from discovery to a closed intake. No AI required. Every phase with every command, typed by a human.
The reference below explains what runs inside each gate. Use it when you need full control or are debugging a step.
On this page
Pipeline overview
| # | Phase | What you produce | Gate |
|---|---|---|---|
| 1 | gaia-curate | A discovery-packet-v2 JSON in registry-for-review/discovery-packets/ | Human L4 |
| 2 | L4 Review | You append l4Resolution to the packet | Hard stop — must be you |
| 3 | gaia push → PR | Intake issue opened; draft PR on a review/meta branch | CI green |
| 4 | ev-pipeline | Verified evidence lake ready for ingest | Human approves evidence |
| 5 | gaia-ingest | Evidence rows written, TM appraised, stars calibrated | Human approves calibration |
| 6 | Close | PR merged, intake issue closed with findings comment | Done |
gaia-curate — Discover & package the skill
You have a real repo with a SKILL.md. Run prefill, apply the 6-rule mapping decision, write the packet, validate. Nothing touches the registry yet.
Step 1 — Preflight
# confirm gaia CLI is installed gaia --version # confirm gh CLI is authenticated gh auth status # confirm python3 available python3 --version
Step 2 — Snapshot the generic list
Save this file. It's the trust anchor for packet validation. Don't overwrite it mid-run.
gaia dev list --generic --json > /tmp/generic-snapshot.json wc -l /tmp/generic-snapshot.json
Step 3 — Run prefill against the SKILL.md URL
gaia dev prefill \ --source "https://github.com/owner/repo/blob/main/SKILL.md" \ --output /tmp/prefill-output.json cat /tmp/prefill-output.json | python3 -m json.tool | head -80
Step 4 — Apply the 6-rule mapping decision
| Rule (first match wins) | Decision | When |
|---|---|---|
| 1 | NOT_A_SKILL | artifactGate != "valid-skill" |
| 2 | DUPLICATE | exactDedupe != null |
| 3 | DEFER | ambiguity != null |
| 4 | NEW_GENERIC | nTotal == 0 |
| 5 | MAP | nStrong == 1 — use that genericId |
| 6 | DEFER | All other cases (weak only, or nStrong ≥ 2) |
Count nStrong = entries with matchTier == "strong" in mappingOptions[]. Count nTotal = total entries. Do not re-rank.
Step 5 — Write and validate the discovery-packet-v2
Create the packet at registry-for-review/discovery-packets/owner--skill-name.json. Key fields:
{
"schemaVersion": "discovery-packet-v2",
"source": { "url": "<blob-url>", "canonicalUrl": "<blob-url>", "lane": "github-skill-file" },
"normalized": { "name": "verbatim from frontmatter", "description": "verbatim" },
"contentSha256": "<sha256 of SKILL.md content>",
"exactDedupe": null,
"mappingOptions": [ /* copy from prefill-output.json */ ],
"decision": "MAP",
"reasonCode": "MAP_EXISTING_GENERIC",
"selectedGenericId": "<id from strong option>",
"genericSnapshot": { "command": "gaia dev list --generic --json", "contentSha256": "<hash>", "generics": [ /* snapshot contents */ ] },
"lifecycle": "review-ready"
}
python3 scripts/validate_discovery_packet.py \ --generic-snapshot /tmp/generic-snapshot.json \ registry-for-review/discovery-packets/owner--skill-name.json # Must exit 0 with no MALFORMED_PACKET or MISSING_REQUIRED_FIELD errors
L4 Review — You ratify the topology
No one else does this step. Check the packet, append l4Resolution, re-validate.
What to check
- Mapping decision is correct — does
selectedGenericIdmatch the skill's actual capability? - If
NEW_GENERIC: is the proposed name and description vendor-neutral and falsifiable? source.urlis a realblob/GitHub URL — nottree/or a listing page.normalized.descriptionis verbatim from theSKILL.mdfrontmatter — not paraphrased.- Similarity score (
mappingOptions[].similarity) andmatchTiermake sense.
Append l4Resolution
"l4Resolution": { "generic": { "id": "final-generic-id", "name": "Human Readable Name", "description": "Vendor-neutral, falsifiable.", "type": "basic", "prerequisites": [] }, "named": { "contributor": "github-handle", "skillName": "kebab-case-name" }, "upstreamSkillFileUrl": "https://github.com/owner/repo/blob/main/SKILL.md" }
python3 scripts/validate_discovery_packet.py \ --generic-snapshot /tmp/generic-snapshot.json \ registry-for-review/discovery-packets/owner--skill-name.json
gaia push → Draft PR — Open the intake issue
git checkout -b review/meta/github-handle--skill-name # Dry run first gaia push --from-file registry-for-review/discovery-packets/owner--skill-name.json --dry-run # Real run — opens intake issue (auto-labels: intake + needs-triage) gaia push --from-file registry-for-review/discovery-packets/owner--skill-name.json git add registry-for-review/discovery-packets/owner--skill-name.json git commit -m "feat(intake): curate contributor/skill-name [closes #ISSUE]" git push -u origin review/meta/github-handle--skill-name gh pr create --draft --title "feat(intake): ..." --body-file /tmp/pr-body.md
intake:* label lifecycle
These are machine gates — intake-approval.yml watches for them and fires automatically.
| Label | Who applies | What it triggers |
|---|---|---|
intake | Auto (gaia push) | Routes into intake queue |
needs-triage | Auto (gaia push) | Marks as awaiting review |
intake:topology-approved | Maintainer only | Workflow fires: adds evidence-review, removes needs-triage |
intake:evidence-review | Auto (workflow) | Signals agent to prepare Stage-1 seed |
intake:evidence-ready | Agent / you | Evidence plan ready for human approval |
intake:evidence-approved | Maintainer only | Opens the single draft promotion PR |
intake:rejected | Maintainer only | Closes intake; no automation fires |
intake:evidence-approved requires both intake:evidence-review and intake:evidence-ready to already be present. The workflow errors if either is missing.
gh issue edit <ISSUE_NUMBER> --add-label "intake:topology-approved" # Fires intake-approval.yml — watch it: gh run list --workflow=intake-approval.yml
ev-pipeline — Verify evidence before ingesting
Operates on evidence/by-type/ files only. Never touches registry/. Each phase produces review artifacts; you decide what to approve.
Phase 0 — ev-discovery (skippable)
The only phase that searches the web for new evidence. Skip for routine Stage-1 intakes. Run when you need benchmark-result, arxiv, peer-review, or richer social-signal rows.
Requires FIRECRAWL_API_KEY. Skip gracefully if absent.
gaia dev discover \ --skill contributor/skill-id \ --repo "https://github.com/owner/repo" \ --types benchmark-result,arxiv,peer-review,social-signal \ --output evidence/discovery/contributor--skill-id.md
Phase 1 — ev-collection
This runs on the entire registry — not just your new skill. generate_source_dump.py reads all named-skill evidence rows across every skill in registry/named/. Your new skill's rows appear alongside all others. That is expected.
python3 evidence/scripts/generate_source_dump.py \ --output-dir evidence --by-type-dir evidence/by-type python3 evidence/scripts/compile_data_lake.py \ --sources evidence/by-type --lake evidence
Phase 2 — ev-star-verification
# Check auth first — zero stars from an unauth'd call is poison data gh auth status gh api repos/OWNER/REPO --jq '.stargazers_count' # Flag rows where recorded stars differ from live count. Do NOT silently update.
Phase 3 — ev-adversarial-audit
# Find github tree/ URLs that should be blob/ grep -rn "github.com/.*/tree/" evidence/by-type/ # Find subjective wording not backed by source grep -rni "elite\|high-quality\|best-in-class\|leading" evidence/by-type/
Phase 4 — ev-link-validation
python3 evidence/scripts/validate_sources.py # Or a 10-URL sample first: python3 evidence/scripts/validate_sources.py 10
gaia-ingest — Write evidence to the named skill
First time mutating registry/. Every row uses --no-build. One build at the end. You approve calibration before it runs.
Ingest each approved evidence row
GAIA_OPERATOR_OVERRIDE=1 gaia dev evidence contributor/skill-id \ "https://github.com/owner/repo" \ --type repo-own --commits 847 --contributors 12 \ --notes "Official upstream repo. Counts verified via GitHub API." \ --source-started-at 2024-03-01 --no-build
GAIA_OPERATOR_OVERRIDE=1 gaia dev evidence contributor/skill-id \ "https://github.com/owner/repo/blob/main/SKILL.md" \ --type github-stars-own --stars 3421 --skill-count-in-repo 1 \ --notes "Official SKILL.md. Star count verified live via gh api." \ --source-started-at 2024-03-01 --no-build
# Single build after all rows are written GAIA_OPERATOR_OVERRIDE=1 gaia dev build # Appraise Trust Magnitude PYTHONPATH=src python3 scripts/trust_appraise.py --skill contributor/skill-id # Only after you approve the proposed calibration: GAIA_OPERATOR_OVERRIDE=1 gaia dev calibrate contributor/skill-id --stars 2 GAIA_OPERATOR_OVERRIDE=1 gaia dev validate
TM grade reference
Trust Magnitude is the sole promotion gate under Yggdrasil II. Thresholds sourced from src/gaia_cli/grading.py and META.md §1.1.
| Grade | TM floor | Stars it gates | Notes |
|---|---|---|---|
| ungraded | < 20 | 1★–2★ | Stage-1 minimum (Awakened / Named baseline) |
| C | ≥ 20 | up to 3★ | Badge unlock floor at 2★ Named |
| B | ≥ 50 | up to 3★ | Solid adoption signals (Evolved) |
| A | ≥ 100 | gates 4★ | 4★ Extra/Unique gate — Origin + TM ≥ 100 |
| S | ≥ 250 + diversity | gates 5★–6★ | Diversity gate: ≥3 evidence types + non-self-producible row. 5★ = TM ≥ 250. 6★ Apex adds 6-predicate gate. |
The per-star Evidence Floor is retired. TM is the sole gate. But the Star Bar (installability, 3★+ requires a verified GitHub blob/ link) still applies.
Close — Merge PR & post intake comments
gh pr ready <PR_NUMBER> gh pr checks <PR_NUMBER> # When CI is green: gh pr merge <PR_NUMBER> --subject "feat(registry): ingest contributor/skill-name [closes #ISSUE]" # Post findings comment on PR (evidence table + TM + badge status) gh pr comment <PR_NUMBER> --body-file /tmp/pr-close-comment.md # Post closing comment on intake issue (path-to-promotion, @contributor tag) gh issue comment <ISSUE_NUMBER> --body-file /tmp/issue-close-comment.md gh issue close <ISSUE_NUMBER> # Regenerate Class S site artifacts GAIA_OPERATOR_OVERRIDE=1 gaia dev docs git add docs/graph/ && git commit -m "chore: regenerate Class S artifacts" && git push
Common errors
UNTRUSTED_GENERIC_SNAPSHOT
The contentSha256 in the packet doesn't match the snapshot file passed to --generic-snapshot.
python3 -c "import json,hashlib; d=json.load(open('/tmp/generic-snapshot.json')); print(hashlib.sha256(json.dumps(d,sort_keys=True,separators=(',',':')).encode()).hexdigest())"
INVALID_GENERIC_SELECTION — mapped ID not in snapshot
You used a genericId that wasn't in the snapshot you captured. Re-capture the snapshot after adding the new generic, or use an ID that's actually there.
gaia dev evidence fails — "unknown evidence type"
gaia dev evidence --help # Lists all supported --type values and required flags
gaia dev validate fails after ingest
GAIA_OPERATOR_OVERRIDE=1 gaia dev validate --verbose # Read the first error — usually a missing field or schema mismatch
Cheat sheet — every command in order
# ── Phase 1: Curate ────────────────────────────────────────── gaia dev list --generic --json > /tmp/generic-snapshot.json gaia dev prefill --source "<blob-url>" --output /tmp/prefill-output.json # ... write packet JSON ... python3 scripts/validate_discovery_packet.py --generic-snapshot /tmp/generic-snapshot.json <packet>.json # ── Phase 2: L4 ────────────────────────────────────────────── # Append l4Resolution to packet, re-validate # ── Phase 3: Push + PR ─────────────────────────────────────── git checkout -b review/meta/handle--skill gaia push --from-file <packet>.json --dry-run gaia push --from-file <packet>.json # auto-labels issue: intake + needs-triage git add . && git commit -m "feat(intake): ..." && git push -u origin <branch> gh pr create --draft --title "..." --body-file /tmp/pr-body.md gh issue edit <ISSUE> --add-label "intake:topology-approved" # maintainer only gh issue edit <ISSUE> --add-label "intake:evidence-approved" # maintainer only, after evidence-ready # ── Phase 4: ev-pipeline ───────────────────────────────────── # Phase 0 (skippable) gaia dev discover --skill contributor/skill --repo "<url>" --types arxiv,peer-review,social-signal # Phase 1 (whole-registry lake rebuild) python3 evidence/scripts/generate_source_dump.py --output-dir evidence --by-type-dir evidence/by-type python3 evidence/scripts/compile_data_lake.py --sources evidence/by-type --lake evidence gh api repos/OWNER/REPO --jq '.stargazers_count' # phase 2 star check grep -rn "github.com/.*/tree/" evidence/by-type/ # phase 3 adversarial python3 evidence/scripts/validate_sources.py # phase 4 link health # ── Phase 5: gaia-ingest ───────────────────────────────────── GAIA_OPERATOR_OVERRIDE=1 gaia dev evidence contributor/skill "<url>" \ --type repo-own --commits N --contributors N --notes "..." --source-started-at YYYY-MM-DD --no-build # ... repeat for each evidence type ... GAIA_OPERATOR_OVERRIDE=1 gaia dev build PYTHONPATH=src python3 scripts/trust_appraise.py --skill contributor/skill GAIA_OPERATOR_OVERRIDE=1 gaia dev calibrate contributor/skill --stars N # after your approval GAIA_OPERATOR_OVERRIDE=1 gaia dev validate # ── Phase 6: Close ─────────────────────────────────────────── gh pr ready <PR> && gh pr checks <PR> gh pr merge <PR> --subject "feat(registry): ... [closes #ISSUE]" gh pr comment <PR> --body-file /tmp/pr-close-comment.md gh issue comment <ISSUE> --body-file /tmp/issue-close-comment.md gh issue close <ISSUE> GAIA_OPERATOR_OVERRIDE=1 gaia dev docs
Want to automate this? Become a contributor.
Once you've curated a skill manually, you can contribute back to the registry directly using gaia dev commands — the same CLI the pipeline runs under the hood. No intake queue. Direct mutations with your approval.
| What you want to do | Command |
|---|---|
| Add a generic skill node | gaia dev add "Name" --id kebab-id --type basic --description "..." |
| Add a named implementation | gaia dev named --contributor handle --skill slug --generic id --upstream <blob-url> |
| Add an evidence row | gaia dev evidence contributor/skill "<url>" --type repo-own --commits N ... |
| Appraise Trust Magnitude | PYTHONPATH=src python3 scripts/trust_appraise.py --skill contributor/skill |
| Calibrate star level | gaia dev calibrate contributor/skill --stars N |
| Fuse a suite capstone | gaia dev fuse <id> --name "..." --prereqs id1,id2 --named-capstone contributor/slug |
| Validate registry | GAIA_OPERATOR_OVERRIDE=1 gaia dev validate |
| Regenerate site artifacts | GAIA_OPERATOR_OVERRIDE=1 gaia dev docs |
All gaia dev mutations require GAIA_OPERATOR_OVERRIDE=1 or maintainer permissions. Read Contributing §1C before making direct registry changes. Or run gaia curate <url> to automate the full pipeline with 2 human gates.