create-egregore 0.20.2 → 0.21.0-runtime-mvp.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/assets/egregore-launcher.js +1013 -16
- package/bin/cli.js +11 -0
- package/lib/claude-runtime.js +192 -0
- package/lib/local.js +38 -31
- package/lib/pi-runtime.js +1 -0
- package/lib/prime-runtime.js +1 -0
- package/lib/runtime-identity.js +146 -0
- package/lib/setup.js +116 -17
- package/package.json +10 -6
- package/runtime/claude/.claude/context/commit-format.md +110 -0
- package/runtime/claude/.claude/context/git-language.md +46 -0
- package/runtime/claude/.claude/context/notification-consent.md +66 -0
- package/runtime/claude/.claude/context/pr-format.md +67 -0
- package/runtime/claude/.claude/context/telemetry.md +133 -0
- package/runtime/claude/.claude/hooks/boundary-check.sh +333 -0
- package/runtime/claude/.claude/hooks/branch-guard.sh +231 -0
- package/runtime/claude/.claude/hooks/card-context.sh +38 -0
- package/runtime/claude/.claude/hooks/emissary-detect.sh +53 -0
- package/runtime/claude/.claude/hooks/memory-refresh.sh +67 -0
- package/runtime/claude/.claude/hooks/onboarding-guard.sh +86 -0
- package/runtime/claude/.claude/hooks/retrieval-context.sh +43 -0
- package/runtime/claude/.claude/rules/voice-bedrock.md +73 -0
- package/runtime/claude/.claude/settings.json +131 -0
- package/runtime/claude/.claude/skills/activity/SKILL.md +68 -0
- package/runtime/claude/.claude/skills/announce/SKILL.md +54 -0
- package/runtime/claude/.claude/skills/archive/SKILL.md +71 -0
- package/runtime/claude/.claude/skills/branch/SKILL.md +147 -0
- package/runtime/claude/.claude/skills/checkup/SKILL.md +159 -0
- package/runtime/claude/.claude/skills/commit/SKILL.md +103 -0
- package/runtime/claude/.claude/skills/contribute/SKILL.md +343 -0
- package/runtime/claude/.claude/skills/create-skill/SKILL.md +135 -0
- package/runtime/claude/.claude/skills/dark-mode/SKILL.md +410 -0
- package/runtime/claude/.claude/skills/dashboard/SKILL.md +43 -0
- package/runtime/claude/.claude/skills/deep-reflect/REPORT.md +140 -0
- package/runtime/claude/.claude/skills/deep-reflect/RESEARCH.md +132 -0
- package/runtime/claude/.claude/skills/deep-reflect/ROLES.md +104 -0
- package/runtime/claude/.claude/skills/deep-reflect/SKILL.md +170 -0
- package/runtime/claude/.claude/skills/delete-user/SKILL.md +150 -0
- package/runtime/claude/.claude/skills/emissary/SKILL.md +220 -0
- package/runtime/claude/.claude/skills/handoff/SKILL.md +124 -0
- package/runtime/claude/.claude/skills/harvest/AUDIT.md +546 -0
- package/runtime/claude/.claude/skills/harvest/FORMAT.md +436 -0
- package/runtime/claude/.claude/skills/harvest/PROCESS.md +395 -0
- package/runtime/claude/.claude/skills/harvest/QUESTION_PALETTE.md +76 -0
- package/runtime/claude/.claude/skills/harvest/SKILL.md +100 -0
- package/runtime/claude/.claude/skills/ingest/SKILL.md +112 -0
- package/runtime/claude/.claude/skills/ingest-corpus/SKILL.md +187 -0
- package/runtime/claude/.claude/skills/ingest-notion/SKILL.md +214 -0
- package/runtime/claude/.claude/skills/ingest-user-interview/SKILL.md +65 -0
- package/runtime/claude/.claude/skills/ingest-user-interview/references/analysis-contract.md +125 -0
- package/runtime/claude/.claude/skills/invite/SKILL.md +111 -0
- package/runtime/claude/.claude/skills/issue/SKILL.md +104 -0
- package/runtime/claude/.claude/skills/me/SKILL.md +81 -0
- package/runtime/claude/.claude/skills/meeting/SKILL.md +76 -0
- package/runtime/claude/.claude/skills/meeting/references/analysis-contract.md +102 -0
- package/runtime/claude/.claude/skills/note/SKILL.md +71 -0
- package/runtime/claude/.claude/skills/notion-connect/SKILL.md +124 -0
- package/runtime/claude/.claude/skills/onboarding/SKILL.md +159 -0
- package/runtime/claude/.claude/skills/pr/SKILL.md +85 -0
- package/runtime/claude/.claude/skills/pull/SKILL.md +79 -0
- package/runtime/claude/.claude/skills/push/SKILL.md +47 -0
- package/runtime/claude/.claude/skills/quest/SKILL.md +121 -0
- package/runtime/claude/.claude/skills/reflect/SKILL.md +69 -0
- package/runtime/claude/.claude/skills/review-pr/SKILL.md +276 -0
- package/runtime/claude/.claude/skills/save/SKILL.md +92 -0
- package/runtime/claude/.claude/skills/slack-connect/SKILL.md +148 -0
- package/runtime/claude/.claude/skills/summon/SKILL.md +240 -0
- package/runtime/claude/.claude/skills/sync-repos/SKILL.md +82 -0
- package/runtime/claude/.claude/skills/teams-connect/SKILL.md +216 -0
- package/runtime/claude/.claude/skills/telegram-connect/SKILL.md +110 -0
- package/runtime/claude/.claude/skills/telemetry/SKILL.md +117 -0
- package/runtime/claude/.claude/skills/test/SKILL.md +87 -0
- package/runtime/claude/.claude/skills/the-spiral/SKILL.md +492 -0
- package/runtime/claude/.claude/skills/tui-design/SKILL.md +188 -0
- package/runtime/claude/.claude/skills/tutorial/SKILL.md +100 -0
- package/runtime/claude/.claude/skills/update/SKILL.md +265 -0
- package/runtime/claude/.claude/skills/view/SKILL.md +393 -0
- package/runtime/claude/.claude/skills/view/compose-scaffold.html +221 -0
- package/runtime/claude/.claude/skills/visual-explain/SKILL.md +132 -0
- package/runtime/claude/.claude/skills/wrap/SKILL.md +98 -0
- package/runtime/claude/CLAUDE.md +447 -0
- package/runtime/claude/bin/activity-action.sh +92 -0
- package/runtime/claude/bin/activity-data.sh +17 -0
- package/runtime/claude/bin/agent.sh +783 -0
- package/runtime/claude/bin/artifact-register.sh +164 -0
- package/runtime/claude/bin/artifact-writeback.sh +53 -0
- package/runtime/claude/bin/artifacts.sh +288 -0
- package/runtime/claude/bin/attendant.sh +707 -0
- package/runtime/claude/bin/autosave.sh +112 -0
- package/runtime/claude/bin/boundary.sh +253 -0
- package/runtime/claude/bin/build-sealed-dataroom.mjs +722 -0
- package/runtime/claude/bin/capture-reconcile.sh +69 -0
- package/runtime/claude/bin/capture-run.sh +357 -0
- package/runtime/claude/bin/codex-install-skills.sh +78 -0
- package/runtime/claude/bin/codex-render-spec.mjs +462 -0
- package/runtime/claude/bin/codex-session-start.sh +275 -0
- package/runtime/claude/bin/codex-skill-render.mjs +349 -0
- package/runtime/claude/bin/codex-sync-skills.sh +237 -0
- package/runtime/claude/bin/connect-refresh.sh +33 -0
- package/runtime/claude/bin/contribute-guard.sh +79 -0
- package/runtime/claude/bin/corpus_map.py +806 -0
- package/runtime/claude/bin/corpus_survey.py +304 -0
- package/runtime/claude/bin/dashboard-data.sh +18 -0
- package/runtime/claude/bin/github-auth.sh +121 -0
- package/runtime/claude/bin/graph-batch.sh +86 -0
- package/runtime/claude/bin/graph-op.sh +1106 -0
- package/runtime/claude/bin/graph-projection.sh +54 -0
- package/runtime/claude/bin/graph-wal.sh +242 -0
- package/runtime/claude/bin/graph.sh +267 -0
- package/runtime/claude/bin/handoff-lifecycle-job.sh +146 -0
- package/runtime/claude/bin/handoff-lifecycle.sh +280 -0
- package/runtime/claude/bin/handoff-pr-backfill.sh +86 -0
- package/runtime/claude/bin/handoff-preview.sh +169 -0
- package/runtime/claude/bin/handoff-run.sh +692 -0
- package/runtime/claude/bin/handoff-save-egregore.sh +224 -0
- package/runtime/claude/bin/index-handoff.sh +322 -0
- package/runtime/claude/bin/ingest-graph.sh +86 -0
- package/runtime/claude/bin/ingest-item.sh +10 -0
- package/runtime/claude/bin/ingest-surface.html +495 -0
- package/runtime/claude/bin/ingest.py +1011 -0
- package/runtime/claude/bin/ingest.sh +308 -0
- package/runtime/claude/bin/ingest_graph.py +856 -0
- package/runtime/claude/bin/ingest_surface.py +544 -0
- package/runtime/claude/bin/invite.sh +6 -0
- package/runtime/claude/bin/issue.sh +10 -0
- package/runtime/claude/bin/knowledge.sh +10 -0
- package/runtime/claude/bin/lib/artifact-id.sh +46 -0
- package/runtime/claude/bin/lib/config.sh +136 -0
- package/runtime/claude/bin/lib/context.sh +642 -0
- package/runtime/claude/bin/lib/dashboard-artifact.sh +242 -0
- package/runtime/claude/bin/lib/ensure-develop.sh +183 -0
- package/runtime/claude/bin/lib/git-message.sh +37 -0
- package/runtime/claude/bin/lib/git-sync.sh +494 -0
- package/runtime/claude/bin/lib/greeting.sh +548 -0
- package/runtime/claude/bin/lib/handoff-meta.sh +97 -0
- package/runtime/claude/bin/lib/hash.sh +13 -0
- package/runtime/claude/bin/lib/identity.sh +213 -0
- package/runtime/claude/bin/lib/metrics.sh +374 -0
- package/runtime/claude/bin/lib/noncode.sh +31 -0
- package/runtime/claude/bin/lib/permissions.sh +106 -0
- package/runtime/claude/bin/lib/time.sh +56 -0
- package/runtime/claude/bin/lib/worktree-links.sh +85 -0
- package/runtime/claude/bin/node-run.sh +42 -0
- package/runtime/claude/bin/notification.sh +6 -0
- package/runtime/claude/bin/notify.sh +636 -0
- package/runtime/claude/bin/observe-context.sh +14 -0
- package/runtime/claude/bin/onboarding.sh +6 -0
- package/runtime/claude/bin/person.py +634 -0
- package/runtime/claude/bin/person.sh +481 -0
- package/runtime/claude/bin/pi-render-spec.mjs +140 -0
- package/runtime/claude/bin/post-update.sh +37 -0
- package/runtime/claude/bin/prime-render-spec.mjs +147 -0
- package/runtime/claude/bin/publish-artifact.sh +324 -0
- package/runtime/claude/bin/publish-references.sh +144 -0
- package/runtime/claude/bin/quest.sh +9 -0
- package/runtime/claude/bin/question.sh +8 -0
- package/runtime/claude/bin/repo-state.sh +96 -0
- package/runtime/claude/bin/research-ingest.sh +7 -0
- package/runtime/claude/bin/restore-owned-skills.sh +67 -0
- package/runtime/claude/bin/retrieval_eval.py +385 -0
- package/runtime/claude/bin/runtime-identity.sh +70 -0
- package/runtime/claude/bin/runtime-upgrade.sh +43 -0
- package/runtime/claude/bin/scroll.sh +9 -0
- package/runtime/claude/bin/search.sh +318 -0
- package/runtime/claude/bin/session-autosave.sh +220 -0
- package/runtime/claude/bin/session-log.sh +199 -0
- package/runtime/claude/bin/session-start.sh +696 -0
- package/runtime/claude/bin/settings.sh +532 -0
- package/runtime/claude/bin/startup-check.sh +136 -0
- package/runtime/claude/bin/statusline.sh +41 -0
- package/runtime/claude/bin/telemetry.sh +666 -0
- package/runtime/claude/bin/test-changes.sh +344 -0
- package/runtime/claude/bin/thread.sh +9 -0
- package/runtime/claude/bin/todo.sh +9 -0
- package/runtime/claude/bin/view-render.sh +126 -0
- package/runtime/claude/bin/worktree-create.sh +145 -0
- package/runtime/claude/bin/worktree-remove.sh +50 -0
- package/runtime/claude/bin/worktree.sh +198 -0
- package/runtime/claude/egregore_runtime/__init__.py +228 -0
- package/runtime/claude/egregore_runtime/adapters/__init__.py +5 -0
- package/runtime/claude/egregore_runtime/adapters/invitation.py +237 -0
- package/runtime/claude/egregore_runtime/adapters/notification.py +59 -0
- package/runtime/claude/egregore_runtime/adapters/qmd.py +1701 -0
- package/runtime/claude/egregore_runtime/adapters/qmd_cli.py +210 -0
- package/runtime/claude/egregore_runtime/adapters/qmd_embed_worker.py +59 -0
- package/runtime/claude/egregore_runtime/admin_gate.py +102 -0
- package/runtime/claude/egregore_runtime/artifacts.py +523 -0
- package/runtime/claude/egregore_runtime/contracts.py +499 -0
- package/runtime/claude/egregore_runtime/entitlements.py +85 -0
- package/runtime/claude/egregore_runtime/errors.py +10 -0
- package/runtime/claude/egregore_runtime/graph.py +356 -0
- package/runtime/claude/egregore_runtime/handoff_lookup.py +196 -0
- package/runtime/claude/egregore_runtime/harness_cli.py +1221 -0
- package/runtime/claude/egregore_runtime/identity.py +734 -0
- package/runtime/claude/egregore_runtime/identity_cli.py +91 -0
- package/runtime/claude/egregore_runtime/ingest.py +575 -0
- package/runtime/claude/egregore_runtime/ingest_cli.py +254 -0
- package/runtime/claude/egregore_runtime/ingest_index_cli.py +147 -0
- package/runtime/claude/egregore_runtime/invitation_cli.py +51 -0
- package/runtime/claude/egregore_runtime/invitations.py +116 -0
- package/runtime/claude/egregore_runtime/issue_cli.py +305 -0
- package/runtime/claude/egregore_runtime/issues.py +359 -0
- package/runtime/claude/egregore_runtime/knowledge.py +376 -0
- package/runtime/claude/egregore_runtime/knowledge_cli.py +173 -0
- package/runtime/claude/egregore_runtime/lifecycle.py +888 -0
- package/runtime/claude/egregore_runtime/lifecycle_cli.py +269 -0
- package/runtime/claude/egregore_runtime/notification_cli.py +125 -0
- package/runtime/claude/egregore_runtime/notifications.py +230 -0
- package/runtime/claude/egregore_runtime/observe.py +342 -0
- package/runtime/claude/egregore_runtime/onboarding.py +290 -0
- package/runtime/claude/egregore_runtime/onboarding_cli.py +110 -0
- package/runtime/claude/egregore_runtime/policy.py +144 -0
- package/runtime/claude/egregore_runtime/profile.py +193 -0
- package/runtime/claude/egregore_runtime/quest_cli.py +216 -0
- package/runtime/claude/egregore_runtime/question_cli.py +180 -0
- package/runtime/claude/egregore_runtime/questions.py +304 -0
- package/runtime/claude/egregore_runtime/quests.py +419 -0
- package/runtime/claude/egregore_runtime/readiness.py +379 -0
- package/runtime/claude/egregore_runtime/research_ingest.py +256 -0
- package/runtime/claude/egregore_runtime/research_ingest_cli.py +44 -0
- package/runtime/claude/egregore_runtime/runtime.py +464 -0
- package/runtime/claude/egregore_runtime/scroll_cli.py +185 -0
- package/runtime/claude/egregore_runtime/scrolls.py +726 -0
- package/runtime/claude/egregore_runtime/status.py +412 -0
- package/runtime/claude/egregore_runtime/status_cli.py +174 -0
- package/runtime/claude/egregore_runtime/sync.py +218 -0
- package/runtime/claude/egregore_runtime/teamsync.py +139 -0
- package/runtime/claude/egregore_runtime/telemetry.py +640 -0
- package/runtime/claude/egregore_runtime/thread_cli.py +173 -0
- package/runtime/claude/egregore_runtime/threads.py +517 -0
- package/runtime/claude/egregore_runtime/todo_cli.py +142 -0
- package/runtime/claude/egregore_runtime/todos.py +244 -0
- package/runtime/claude/egregore_runtime/upgrade.py +770 -0
- package/runtime/claude/egregore_runtime/upgrade_worker.py +53 -0
- package/runtime/claude/egregore_runtime/writeback.py +391 -0
- package/runtime/claude/egregore_runtime/writeback_cli.py +114 -0
- package/runtime/claude/manifest.json +284 -0
- package/runtime/codex/.codex/hooks/search-hint.js +21 -52
- package/runtime/codex/.codex/hooks.json +3 -3
- package/runtime/codex/.codex/skills/activity/SKILL.md +23 -66
- package/runtime/codex/.codex/skills/announce/SKILL.md +27 -50
- package/runtime/codex/.codex/skills/archive/SKILL.md +21 -36
- package/runtime/codex/.codex/skills/checkup/SKILL.md +77 -36
- package/runtime/codex/.codex/skills/dark-mode/SKILL.md +1 -1
- package/runtime/codex/.codex/skills/dashboard/SKILL.md +17 -47
- package/runtime/codex/.codex/skills/handoff/SKILL.md +84 -133
- package/runtime/codex/.codex/skills/harvest/SKILL.md +32 -117
- package/runtime/codex/.codex/skills/ingest/SKILL.md +47 -25
- package/runtime/codex/.codex/skills/ingest-user-interview/SKILL.md +18 -36
- package/runtime/codex/.codex/skills/ingest-user-interview/references/analysis-contract.md +42 -0
- package/runtime/codex/.codex/skills/invite/SKILL.md +21 -35
- package/runtime/codex/.codex/skills/issue/SKILL.md +60 -41
- package/runtime/codex/.codex/skills/me/SKILL.md +1 -1
- package/runtime/codex/.codex/skills/meeting/SKILL.md +16 -36
- package/runtime/codex/.codex/skills/meeting/references/analysis-contract.md +48 -0
- package/runtime/codex/.codex/skills/note/SKILL.md +30 -25
- package/runtime/codex/.codex/skills/onboarding/SKILL.md +36 -41
- package/runtime/codex/.codex/skills/pull/SKILL.md +1 -1
- package/runtime/codex/.codex/skills/quest/SKILL.md +27 -66
- package/runtime/codex/.codex/skills/reflect/SKILL.md +22 -36
- package/runtime/codex/.codex/skills/save/SKILL.md +2 -2
- package/runtime/codex/.codex/skills/telemetry/SKILL.md +1 -1
- package/runtime/codex/.codex/skills/test/SKILL.md +1 -1
- package/runtime/codex/.codex/skills/tutorial/SKILL.md +40 -41
- package/runtime/codex/.codex/skills/view/SKILL.md +115 -111
- package/runtime/codex/.codex/skills/wrap/SKILL.md +45 -41
- package/runtime/codex/.codex/spec-manifest.json +9 -9
- package/runtime/codex/AGENTS.md +62 -58
- package/runtime/codex/bin/activity-action.sh +92 -0
- package/runtime/codex/bin/activity-data.sh +12 -233
- package/runtime/codex/bin/agent.sh +84 -100
- package/runtime/codex/bin/artifact-register.sh +164 -0
- package/runtime/codex/bin/artifact-writeback.sh +53 -0
- package/runtime/codex/bin/artifacts.sh +288 -0
- package/runtime/codex/bin/build-sealed-dataroom.mjs +722 -0
- package/runtime/codex/bin/capture-run.sh +18 -2
- package/runtime/codex/bin/codex-render-spec.mjs +41 -16
- package/runtime/codex/bin/codex-session-start.sh +14 -4
- package/runtime/codex/bin/codex-skill-render.mjs +9 -7
- package/runtime/codex/bin/corpus_map.py +806 -0
- package/runtime/codex/bin/corpus_survey.py +304 -0
- package/runtime/codex/bin/dashboard-data.sh +11 -171
- package/runtime/codex/bin/github-auth.sh +121 -0
- package/runtime/codex/bin/graph-batch.sh +7 -0
- package/runtime/codex/bin/graph-op.sh +4 -0
- package/runtime/codex/bin/graph-projection.sh +54 -0
- package/runtime/codex/bin/graph-wal.sh +13 -0
- package/runtime/codex/bin/graph.sh +44 -0
- package/runtime/codex/bin/handoff-lifecycle-job.sh +146 -0
- package/runtime/codex/bin/handoff-lifecycle.sh +280 -0
- package/runtime/codex/bin/handoff-preview.sh +169 -0
- package/runtime/codex/bin/handoff-run.sh +42 -26
- package/runtime/codex/bin/ingest-graph.sh +6 -0
- package/runtime/codex/bin/ingest-item.sh +10 -0
- package/runtime/codex/bin/ingest.sh +59 -30
- package/runtime/codex/bin/invite.sh +6 -0
- package/runtime/codex/bin/issue.sh +10 -0
- package/runtime/codex/bin/knowledge.sh +10 -0
- package/runtime/codex/bin/lib/config.sh +20 -0
- package/runtime/codex/bin/lib/context.sh +46 -25
- package/runtime/codex/bin/lib/git-sync.sh +70 -6
- package/runtime/codex/bin/lib/greeting.sh +34 -5
- package/runtime/codex/bin/lib/handoff-meta.sh +97 -0
- package/runtime/codex/bin/lib/worktree-links.sh +6 -0
- package/runtime/codex/bin/node-run.sh +42 -0
- package/runtime/codex/bin/notification.sh +6 -0
- package/runtime/codex/bin/observe-context.sh +14 -0
- package/runtime/codex/bin/onboarding.sh +6 -0
- package/runtime/codex/bin/person.py +4 -0
- package/runtime/codex/bin/person.sh +43 -10
- package/runtime/codex/bin/pi-render-spec.mjs +140 -0
- package/runtime/codex/bin/post-update.sh +37 -0
- package/runtime/codex/bin/prime-render-spec.mjs +147 -0
- package/runtime/codex/bin/publish-artifact.sh +55 -2
- package/runtime/codex/bin/quest.sh +9 -0
- package/runtime/codex/bin/question.sh +8 -0
- package/runtime/codex/bin/research-ingest.sh +7 -0
- package/runtime/codex/bin/restore-owned-skills.sh +67 -0
- package/runtime/codex/bin/retrieval_eval.py +385 -0
- package/runtime/codex/bin/runtime-identity.sh +70 -0
- package/runtime/codex/bin/runtime-upgrade.sh +43 -0
- package/runtime/codex/bin/scroll.sh +9 -0
- package/runtime/codex/bin/search.sh +231 -195
- package/runtime/codex/bin/settings.sh +174 -5
- package/runtime/codex/bin/startup-check.sh +136 -0
- package/runtime/codex/bin/telemetry.sh +522 -247
- package/runtime/codex/bin/test-changes.sh +344 -0
- package/runtime/codex/bin/thread.sh +9 -0
- package/runtime/codex/bin/todo.sh +9 -0
- package/runtime/codex/bin/view-render.sh +126 -0
- package/runtime/codex/bin/worktree-create.sh +19 -5
- package/runtime/codex/egregore_runtime/__init__.py +228 -0
- package/runtime/codex/egregore_runtime/adapters/__init__.py +5 -0
- package/runtime/codex/egregore_runtime/adapters/invitation.py +237 -0
- package/runtime/codex/egregore_runtime/adapters/notification.py +59 -0
- package/runtime/codex/egregore_runtime/adapters/qmd.py +1701 -0
- package/runtime/codex/egregore_runtime/adapters/qmd_cli.py +210 -0
- package/runtime/codex/egregore_runtime/adapters/qmd_embed_worker.py +59 -0
- package/runtime/codex/egregore_runtime/admin_gate.py +102 -0
- package/runtime/codex/egregore_runtime/artifacts.py +523 -0
- package/runtime/codex/egregore_runtime/contracts.py +499 -0
- package/runtime/codex/egregore_runtime/entitlements.py +85 -0
- package/runtime/codex/egregore_runtime/errors.py +10 -0
- package/runtime/codex/egregore_runtime/graph.py +356 -0
- package/runtime/codex/egregore_runtime/handoff_lookup.py +196 -0
- package/runtime/codex/egregore_runtime/harness_cli.py +1221 -0
- package/runtime/codex/egregore_runtime/identity.py +734 -0
- package/runtime/codex/egregore_runtime/identity_cli.py +91 -0
- package/runtime/codex/egregore_runtime/ingest.py +575 -0
- package/runtime/codex/egregore_runtime/ingest_cli.py +254 -0
- package/runtime/codex/egregore_runtime/ingest_index_cli.py +147 -0
- package/runtime/codex/egregore_runtime/invitation_cli.py +51 -0
- package/runtime/codex/egregore_runtime/invitations.py +116 -0
- package/runtime/codex/egregore_runtime/issue_cli.py +305 -0
- package/runtime/codex/egregore_runtime/issues.py +359 -0
- package/runtime/codex/egregore_runtime/knowledge.py +376 -0
- package/runtime/codex/egregore_runtime/knowledge_cli.py +173 -0
- package/runtime/codex/egregore_runtime/lifecycle.py +888 -0
- package/runtime/codex/egregore_runtime/lifecycle_cli.py +269 -0
- package/runtime/codex/egregore_runtime/notification_cli.py +125 -0
- package/runtime/codex/egregore_runtime/notifications.py +230 -0
- package/runtime/codex/egregore_runtime/observe.py +342 -0
- package/runtime/codex/egregore_runtime/onboarding.py +290 -0
- package/runtime/codex/egregore_runtime/onboarding_cli.py +110 -0
- package/runtime/codex/egregore_runtime/policy.py +144 -0
- package/runtime/codex/egregore_runtime/profile.py +193 -0
- package/runtime/codex/egregore_runtime/quest_cli.py +216 -0
- package/runtime/codex/egregore_runtime/question_cli.py +180 -0
- package/runtime/codex/egregore_runtime/questions.py +304 -0
- package/runtime/codex/egregore_runtime/quests.py +419 -0
- package/runtime/codex/egregore_runtime/readiness.py +379 -0
- package/runtime/codex/egregore_runtime/research_ingest.py +256 -0
- package/runtime/codex/egregore_runtime/research_ingest_cli.py +44 -0
- package/runtime/codex/egregore_runtime/runtime.py +464 -0
- package/runtime/codex/egregore_runtime/scroll_cli.py +185 -0
- package/runtime/codex/egregore_runtime/scrolls.py +726 -0
- package/runtime/codex/egregore_runtime/status.py +412 -0
- package/runtime/codex/egregore_runtime/status_cli.py +174 -0
- package/runtime/codex/egregore_runtime/sync.py +218 -0
- package/runtime/codex/egregore_runtime/teamsync.py +139 -0
- package/runtime/codex/egregore_runtime/telemetry.py +640 -0
- package/runtime/codex/egregore_runtime/thread_cli.py +173 -0
- package/runtime/codex/egregore_runtime/threads.py +517 -0
- package/runtime/codex/egregore_runtime/todo_cli.py +142 -0
- package/runtime/codex/egregore_runtime/todos.py +244 -0
- package/runtime/codex/egregore_runtime/upgrade.py +770 -0
- package/runtime/codex/egregore_runtime/upgrade_worker.py +53 -0
- package/runtime/codex/egregore_runtime/writeback.py +391 -0
- package/runtime/codex/egregore_runtime/writeback_cli.py +114 -0
- package/runtime/codex/manifest.json +98 -1
- package/runtime/pi/.codex/hooks/search-hint.js +21 -52
- package/runtime/pi/.codex/hooks.json +3 -3
- package/runtime/pi/.codex/skills/activity/SKILL.md +23 -66
- package/runtime/pi/.codex/skills/announce/SKILL.md +27 -50
- package/runtime/pi/.codex/skills/archive/SKILL.md +21 -36
- package/runtime/pi/.codex/skills/checkup/SKILL.md +77 -36
- package/runtime/pi/.codex/skills/dark-mode/SKILL.md +1 -1
- package/runtime/pi/.codex/skills/dashboard/SKILL.md +17 -47
- package/runtime/pi/.codex/skills/handoff/SKILL.md +84 -133
- package/runtime/pi/.codex/skills/harvest/SKILL.md +32 -117
- package/runtime/pi/.codex/skills/ingest/SKILL.md +47 -25
- package/runtime/pi/.codex/skills/ingest-user-interview/SKILL.md +18 -36
- package/runtime/pi/.codex/skills/ingest-user-interview/references/analysis-contract.md +42 -0
- package/runtime/pi/.codex/skills/invite/SKILL.md +21 -35
- package/runtime/pi/.codex/skills/issue/SKILL.md +60 -41
- package/runtime/pi/.codex/skills/me/SKILL.md +1 -1
- package/runtime/pi/.codex/skills/meeting/SKILL.md +16 -36
- package/runtime/pi/.codex/skills/meeting/references/analysis-contract.md +48 -0
- package/runtime/pi/.codex/skills/note/SKILL.md +30 -25
- package/runtime/pi/.codex/skills/onboarding/SKILL.md +36 -41
- package/runtime/pi/.codex/skills/pull/SKILL.md +1 -1
- package/runtime/pi/.codex/skills/quest/SKILL.md +27 -66
- package/runtime/pi/.codex/skills/reflect/SKILL.md +22 -36
- package/runtime/pi/.codex/skills/save/SKILL.md +2 -2
- package/runtime/pi/.codex/skills/telemetry/SKILL.md +1 -1
- package/runtime/pi/.codex/skills/test/SKILL.md +1 -1
- package/runtime/pi/.codex/skills/tutorial/SKILL.md +40 -41
- package/runtime/pi/.codex/skills/view/SKILL.md +115 -111
- package/runtime/pi/.codex/skills/wrap/SKILL.md +45 -41
- package/runtime/pi/.codex/spec-manifest.json +9 -9
- package/runtime/pi/.pi/APPEND_SYSTEM.md +57 -48
- package/runtime/pi/.pi/extensions/egregore.ts +7 -0
- package/runtime/pi/.pi/spec-manifest.json +2 -2
- package/runtime/pi/AGENTS.md +62 -58
- package/runtime/pi/bin/activity-action.sh +92 -0
- package/runtime/pi/bin/activity-data.sh +12 -233
- package/runtime/pi/bin/agent.sh +84 -100
- package/runtime/pi/bin/artifact-register.sh +164 -0
- package/runtime/pi/bin/artifact-writeback.sh +53 -0
- package/runtime/pi/bin/artifacts.sh +288 -0
- package/runtime/pi/bin/build-sealed-dataroom.mjs +722 -0
- package/runtime/pi/bin/capture-run.sh +18 -2
- package/runtime/pi/bin/codex-render-spec.mjs +41 -16
- package/runtime/pi/bin/codex-session-start.sh +14 -4
- package/runtime/pi/bin/codex-skill-render.mjs +9 -7
- package/runtime/pi/bin/corpus_map.py +806 -0
- package/runtime/pi/bin/corpus_survey.py +304 -0
- package/runtime/pi/bin/dashboard-data.sh +11 -171
- package/runtime/pi/bin/github-auth.sh +121 -0
- package/runtime/pi/bin/graph-batch.sh +7 -0
- package/runtime/pi/bin/graph-op.sh +4 -0
- package/runtime/pi/bin/graph-projection.sh +54 -0
- package/runtime/pi/bin/graph-wal.sh +13 -0
- package/runtime/pi/bin/graph.sh +44 -0
- package/runtime/pi/bin/handoff-lifecycle-job.sh +146 -0
- package/runtime/pi/bin/handoff-lifecycle.sh +280 -0
- package/runtime/pi/bin/handoff-preview.sh +169 -0
- package/runtime/pi/bin/handoff-run.sh +42 -26
- package/runtime/pi/bin/ingest-graph.sh +6 -0
- package/runtime/pi/bin/ingest-item.sh +10 -0
- package/runtime/pi/bin/ingest.sh +59 -30
- package/runtime/pi/bin/invite.sh +6 -0
- package/runtime/pi/bin/issue.sh +10 -0
- package/runtime/pi/bin/knowledge.sh +10 -0
- package/runtime/pi/bin/lib/config.sh +20 -0
- package/runtime/pi/bin/lib/context.sh +46 -25
- package/runtime/pi/bin/lib/git-sync.sh +70 -6
- package/runtime/pi/bin/lib/greeting.sh +34 -5
- package/runtime/pi/bin/lib/handoff-meta.sh +97 -0
- package/runtime/pi/bin/lib/worktree-links.sh +6 -0
- package/runtime/pi/bin/node-run.sh +42 -0
- package/runtime/pi/bin/notification.sh +6 -0
- package/runtime/pi/bin/observe-context.sh +14 -0
- package/runtime/pi/bin/onboarding.sh +6 -0
- package/runtime/pi/bin/person.py +4 -0
- package/runtime/pi/bin/person.sh +43 -10
- package/runtime/pi/bin/pi-observe-context.mjs +93 -0
- package/runtime/pi/bin/pi-product-workflows.mjs +1 -1
- package/runtime/pi/bin/pi-render-spec.mjs +1 -1
- package/runtime/pi/bin/post-update.sh +37 -0
- package/runtime/pi/bin/prime-render-spec.mjs +147 -0
- package/runtime/pi/bin/publish-artifact.sh +55 -2
- package/runtime/pi/bin/quest.sh +9 -0
- package/runtime/pi/bin/question.sh +8 -0
- package/runtime/pi/bin/research-ingest.sh +7 -0
- package/runtime/pi/bin/restore-owned-skills.sh +67 -0
- package/runtime/pi/bin/retrieval_eval.py +385 -0
- package/runtime/pi/bin/runtime-identity.sh +70 -0
- package/runtime/pi/bin/runtime-upgrade.sh +43 -0
- package/runtime/pi/bin/scroll.sh +9 -0
- package/runtime/pi/bin/search.sh +231 -195
- package/runtime/pi/bin/settings.sh +174 -5
- package/runtime/pi/bin/startup-check.sh +136 -0
- package/runtime/pi/bin/telemetry.sh +522 -247
- package/runtime/pi/bin/test-changes.sh +344 -0
- package/runtime/pi/bin/thread.sh +9 -0
- package/runtime/pi/bin/todo.sh +9 -0
- package/runtime/pi/bin/view-render.sh +126 -0
- package/runtime/pi/bin/worktree-create.sh +19 -5
- package/runtime/pi/egregore_runtime/__init__.py +228 -0
- package/runtime/pi/egregore_runtime/adapters/__init__.py +5 -0
- package/runtime/pi/egregore_runtime/adapters/invitation.py +237 -0
- package/runtime/pi/egregore_runtime/adapters/notification.py +59 -0
- package/runtime/pi/egregore_runtime/adapters/qmd.py +1701 -0
- package/runtime/pi/egregore_runtime/adapters/qmd_cli.py +210 -0
- package/runtime/pi/egregore_runtime/adapters/qmd_embed_worker.py +59 -0
- package/runtime/pi/egregore_runtime/admin_gate.py +102 -0
- package/runtime/pi/egregore_runtime/artifacts.py +523 -0
- package/runtime/pi/egregore_runtime/contracts.py +499 -0
- package/runtime/pi/egregore_runtime/entitlements.py +85 -0
- package/runtime/pi/egregore_runtime/errors.py +10 -0
- package/runtime/pi/egregore_runtime/graph.py +356 -0
- package/runtime/pi/egregore_runtime/handoff_lookup.py +196 -0
- package/runtime/pi/egregore_runtime/harness_cli.py +1221 -0
- package/runtime/pi/egregore_runtime/identity.py +734 -0
- package/runtime/pi/egregore_runtime/identity_cli.py +91 -0
- package/runtime/pi/egregore_runtime/ingest.py +575 -0
- package/runtime/pi/egregore_runtime/ingest_cli.py +254 -0
- package/runtime/pi/egregore_runtime/ingest_index_cli.py +147 -0
- package/runtime/pi/egregore_runtime/invitation_cli.py +51 -0
- package/runtime/pi/egregore_runtime/invitations.py +116 -0
- package/runtime/pi/egregore_runtime/issue_cli.py +305 -0
- package/runtime/pi/egregore_runtime/issues.py +359 -0
- package/runtime/pi/egregore_runtime/knowledge.py +376 -0
- package/runtime/pi/egregore_runtime/knowledge_cli.py +173 -0
- package/runtime/pi/egregore_runtime/lifecycle.py +888 -0
- package/runtime/pi/egregore_runtime/lifecycle_cli.py +269 -0
- package/runtime/pi/egregore_runtime/notification_cli.py +125 -0
- package/runtime/pi/egregore_runtime/notifications.py +230 -0
- package/runtime/pi/egregore_runtime/observe.py +342 -0
- package/runtime/pi/egregore_runtime/onboarding.py +290 -0
- package/runtime/pi/egregore_runtime/onboarding_cli.py +110 -0
- package/runtime/pi/egregore_runtime/policy.py +144 -0
- package/runtime/pi/egregore_runtime/profile.py +193 -0
- package/runtime/pi/egregore_runtime/quest_cli.py +216 -0
- package/runtime/pi/egregore_runtime/question_cli.py +180 -0
- package/runtime/pi/egregore_runtime/questions.py +304 -0
- package/runtime/pi/egregore_runtime/quests.py +419 -0
- package/runtime/pi/egregore_runtime/readiness.py +379 -0
- package/runtime/pi/egregore_runtime/research_ingest.py +256 -0
- package/runtime/pi/egregore_runtime/research_ingest_cli.py +44 -0
- package/runtime/pi/egregore_runtime/runtime.py +464 -0
- package/runtime/pi/egregore_runtime/scroll_cli.py +185 -0
- package/runtime/pi/egregore_runtime/scrolls.py +726 -0
- package/runtime/pi/egregore_runtime/status.py +412 -0
- package/runtime/pi/egregore_runtime/status_cli.py +174 -0
- package/runtime/pi/egregore_runtime/sync.py +218 -0
- package/runtime/pi/egregore_runtime/teamsync.py +139 -0
- package/runtime/pi/egregore_runtime/telemetry.py +640 -0
- package/runtime/pi/egregore_runtime/thread_cli.py +173 -0
- package/runtime/pi/egregore_runtime/threads.py +517 -0
- package/runtime/pi/egregore_runtime/todo_cli.py +142 -0
- package/runtime/pi/egregore_runtime/todos.py +244 -0
- package/runtime/pi/egregore_runtime/upgrade.py +770 -0
- package/runtime/pi/egregore_runtime/upgrade_worker.py +53 -0
- package/runtime/pi/egregore_runtime/writeback.py +391 -0
- package/runtime/pi/egregore_runtime/writeback_cli.py +114 -0
- package/runtime/pi/manifest.json +98 -1
- package/runtime/prime/.codex/hooks/search-hint.js +21 -52
- package/runtime/prime/.codex/hooks.json +3 -3
- package/runtime/prime/.codex/skills/activity/SKILL.md +23 -66
- package/runtime/prime/.codex/skills/announce/SKILL.md +27 -50
- package/runtime/prime/.codex/skills/archive/SKILL.md +21 -36
- package/runtime/prime/.codex/skills/checkup/SKILL.md +77 -36
- package/runtime/prime/.codex/skills/dark-mode/SKILL.md +1 -1
- package/runtime/prime/.codex/skills/dashboard/SKILL.md +17 -47
- package/runtime/prime/.codex/skills/handoff/SKILL.md +84 -133
- package/runtime/prime/.codex/skills/harvest/SKILL.md +32 -117
- package/runtime/prime/.codex/skills/ingest/SKILL.md +47 -25
- package/runtime/prime/.codex/skills/ingest-user-interview/SKILL.md +18 -36
- package/runtime/prime/.codex/skills/ingest-user-interview/references/analysis-contract.md +42 -0
- package/runtime/prime/.codex/skills/invite/SKILL.md +21 -35
- package/runtime/prime/.codex/skills/issue/SKILL.md +60 -41
- package/runtime/prime/.codex/skills/me/SKILL.md +1 -1
- package/runtime/prime/.codex/skills/meeting/SKILL.md +16 -36
- package/runtime/prime/.codex/skills/meeting/references/analysis-contract.md +48 -0
- package/runtime/prime/.codex/skills/note/SKILL.md +30 -25
- package/runtime/prime/.codex/skills/onboarding/SKILL.md +36 -41
- package/runtime/prime/.codex/skills/pull/SKILL.md +1 -1
- package/runtime/prime/.codex/skills/quest/SKILL.md +27 -66
- package/runtime/prime/.codex/skills/reflect/SKILL.md +22 -36
- package/runtime/prime/.codex/skills/save/SKILL.md +2 -2
- package/runtime/prime/.codex/skills/telemetry/SKILL.md +1 -1
- package/runtime/prime/.codex/skills/test/SKILL.md +1 -1
- package/runtime/prime/.codex/skills/tutorial/SKILL.md +40 -41
- package/runtime/prime/.codex/skills/view/SKILL.md +115 -111
- package/runtime/prime/.codex/skills/wrap/SKILL.md +45 -41
- package/runtime/prime/.codex/spec-manifest.json +9 -9
- package/runtime/prime/.prime/agent/APPEND_SYSTEM.md +57 -48
- package/runtime/prime/.prime/agent/extensions/egregore.ts +7 -0
- package/runtime/prime/.prime/agent/spec-manifest.json +2 -2
- package/runtime/prime/AGENTS.md +62 -58
- package/runtime/prime/bin/activity-action.sh +92 -0
- package/runtime/prime/bin/activity-data.sh +12 -233
- package/runtime/prime/bin/agent.sh +84 -100
- package/runtime/prime/bin/artifact-register.sh +164 -0
- package/runtime/prime/bin/artifact-writeback.sh +53 -0
- package/runtime/prime/bin/artifacts.sh +288 -0
- package/runtime/prime/bin/build-sealed-dataroom.mjs +722 -0
- package/runtime/prime/bin/capture-run.sh +18 -2
- package/runtime/prime/bin/codex-render-spec.mjs +41 -16
- package/runtime/prime/bin/codex-session-start.sh +14 -4
- package/runtime/prime/bin/codex-skill-render.mjs +9 -7
- package/runtime/prime/bin/corpus_map.py +806 -0
- package/runtime/prime/bin/corpus_survey.py +304 -0
- package/runtime/prime/bin/dashboard-data.sh +11 -171
- package/runtime/prime/bin/github-auth.sh +121 -0
- package/runtime/prime/bin/graph-batch.sh +7 -0
- package/runtime/prime/bin/graph-op.sh +4 -0
- package/runtime/prime/bin/graph-projection.sh +54 -0
- package/runtime/prime/bin/graph-wal.sh +13 -0
- package/runtime/prime/bin/graph.sh +44 -0
- package/runtime/prime/bin/handoff-lifecycle-job.sh +146 -0
- package/runtime/prime/bin/handoff-lifecycle.sh +280 -0
- package/runtime/prime/bin/handoff-preview.sh +169 -0
- package/runtime/prime/bin/handoff-run.sh +42 -26
- package/runtime/prime/bin/ingest-graph.sh +6 -0
- package/runtime/prime/bin/ingest-item.sh +10 -0
- package/runtime/prime/bin/ingest.sh +59 -30
- package/runtime/prime/bin/invite.sh +6 -0
- package/runtime/prime/bin/issue.sh +10 -0
- package/runtime/prime/bin/knowledge.sh +10 -0
- package/runtime/prime/bin/lib/config.sh +20 -0
- package/runtime/prime/bin/lib/context.sh +46 -25
- package/runtime/prime/bin/lib/git-sync.sh +70 -6
- package/runtime/prime/bin/lib/greeting.sh +34 -5
- package/runtime/prime/bin/lib/handoff-meta.sh +97 -0
- package/runtime/prime/bin/lib/worktree-links.sh +6 -0
- package/runtime/prime/bin/node-run.sh +42 -0
- package/runtime/prime/bin/notification.sh +6 -0
- package/runtime/prime/bin/observe-context.sh +14 -0
- package/runtime/prime/bin/onboarding.sh +6 -0
- package/runtime/prime/bin/person.py +4 -0
- package/runtime/prime/bin/person.sh +43 -10
- package/runtime/prime/bin/pi-observe-context.mjs +93 -0
- package/runtime/prime/bin/pi-product-workflows.mjs +1 -1
- package/runtime/prime/bin/pi-render-spec.mjs +140 -0
- package/runtime/prime/bin/post-update.sh +37 -0
- package/runtime/prime/bin/prime-render-spec.mjs +1 -1
- package/runtime/prime/bin/publish-artifact.sh +55 -2
- package/runtime/prime/bin/quest.sh +9 -0
- package/runtime/prime/bin/question.sh +8 -0
- package/runtime/prime/bin/research-ingest.sh +7 -0
- package/runtime/prime/bin/restore-owned-skills.sh +67 -0
- package/runtime/prime/bin/retrieval_eval.py +385 -0
- package/runtime/prime/bin/runtime-identity.sh +70 -0
- package/runtime/prime/bin/runtime-upgrade.sh +43 -0
- package/runtime/prime/bin/scroll.sh +9 -0
- package/runtime/prime/bin/search.sh +231 -195
- package/runtime/prime/bin/settings.sh +174 -5
- package/runtime/prime/bin/startup-check.sh +136 -0
- package/runtime/prime/bin/telemetry.sh +522 -247
- package/runtime/prime/bin/test-changes.sh +344 -0
- package/runtime/prime/bin/thread.sh +9 -0
- package/runtime/prime/bin/todo.sh +9 -0
- package/runtime/prime/bin/view-render.sh +126 -0
- package/runtime/prime/bin/worktree-create.sh +19 -5
- package/runtime/prime/egregore_runtime/__init__.py +228 -0
- package/runtime/prime/egregore_runtime/adapters/__init__.py +5 -0
- package/runtime/prime/egregore_runtime/adapters/invitation.py +237 -0
- package/runtime/prime/egregore_runtime/adapters/notification.py +59 -0
- package/runtime/prime/egregore_runtime/adapters/qmd.py +1701 -0
- package/runtime/prime/egregore_runtime/adapters/qmd_cli.py +210 -0
- package/runtime/prime/egregore_runtime/adapters/qmd_embed_worker.py +59 -0
- package/runtime/prime/egregore_runtime/admin_gate.py +102 -0
- package/runtime/prime/egregore_runtime/artifacts.py +523 -0
- package/runtime/prime/egregore_runtime/contracts.py +499 -0
- package/runtime/prime/egregore_runtime/entitlements.py +85 -0
- package/runtime/prime/egregore_runtime/errors.py +10 -0
- package/runtime/prime/egregore_runtime/graph.py +356 -0
- package/runtime/prime/egregore_runtime/handoff_lookup.py +196 -0
- package/runtime/prime/egregore_runtime/harness_cli.py +1221 -0
- package/runtime/prime/egregore_runtime/identity.py +734 -0
- package/runtime/prime/egregore_runtime/identity_cli.py +91 -0
- package/runtime/prime/egregore_runtime/ingest.py +575 -0
- package/runtime/prime/egregore_runtime/ingest_cli.py +254 -0
- package/runtime/prime/egregore_runtime/ingest_index_cli.py +147 -0
- package/runtime/prime/egregore_runtime/invitation_cli.py +51 -0
- package/runtime/prime/egregore_runtime/invitations.py +116 -0
- package/runtime/prime/egregore_runtime/issue_cli.py +305 -0
- package/runtime/prime/egregore_runtime/issues.py +359 -0
- package/runtime/prime/egregore_runtime/knowledge.py +376 -0
- package/runtime/prime/egregore_runtime/knowledge_cli.py +173 -0
- package/runtime/prime/egregore_runtime/lifecycle.py +888 -0
- package/runtime/prime/egregore_runtime/lifecycle_cli.py +269 -0
- package/runtime/prime/egregore_runtime/notification_cli.py +125 -0
- package/runtime/prime/egregore_runtime/notifications.py +230 -0
- package/runtime/prime/egregore_runtime/observe.py +342 -0
- package/runtime/prime/egregore_runtime/onboarding.py +290 -0
- package/runtime/prime/egregore_runtime/onboarding_cli.py +110 -0
- package/runtime/prime/egregore_runtime/policy.py +144 -0
- package/runtime/prime/egregore_runtime/profile.py +193 -0
- package/runtime/prime/egregore_runtime/quest_cli.py +216 -0
- package/runtime/prime/egregore_runtime/question_cli.py +180 -0
- package/runtime/prime/egregore_runtime/questions.py +304 -0
- package/runtime/prime/egregore_runtime/quests.py +419 -0
- package/runtime/prime/egregore_runtime/readiness.py +379 -0
- package/runtime/prime/egregore_runtime/research_ingest.py +256 -0
- package/runtime/prime/egregore_runtime/research_ingest_cli.py +44 -0
- package/runtime/prime/egregore_runtime/runtime.py +464 -0
- package/runtime/prime/egregore_runtime/scroll_cli.py +185 -0
- package/runtime/prime/egregore_runtime/scrolls.py +726 -0
- package/runtime/prime/egregore_runtime/status.py +412 -0
- package/runtime/prime/egregore_runtime/status_cli.py +174 -0
- package/runtime/prime/egregore_runtime/sync.py +218 -0
- package/runtime/prime/egregore_runtime/teamsync.py +139 -0
- package/runtime/prime/egregore_runtime/telemetry.py +640 -0
- package/runtime/prime/egregore_runtime/thread_cli.py +173 -0
- package/runtime/prime/egregore_runtime/threads.py +517 -0
- package/runtime/prime/egregore_runtime/todo_cli.py +142 -0
- package/runtime/prime/egregore_runtime/todos.py +244 -0
- package/runtime/prime/egregore_runtime/upgrade.py +770 -0
- package/runtime/prime/egregore_runtime/upgrade_worker.py +53 -0
- package/runtime/prime/egregore_runtime/writeback.py +391 -0
- package/runtime/prime/egregore_runtime/writeback_cli.py +114 -0
- package/runtime/prime/manifest.json +98 -1
|
@@ -0,0 +1,481 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
set -euo pipefail
|
|
3
|
+
|
|
4
|
+
# Provider-independent identity spine for local state, canonical people files,
|
|
5
|
+
# and the shared control plane. Neo4j is an optional derived projection.
|
|
6
|
+
|
|
7
|
+
ROOT="$(cd "$(dirname "$0")/.." && pwd)"
|
|
8
|
+
SCRIPT_DIR="$ROOT"
|
|
9
|
+
CONFIG="$ROOT/egregore.json"
|
|
10
|
+
STATE="$ROOT/.egregore-state.json"
|
|
11
|
+
PERSON_PY="$ROOT/bin/person.py"
|
|
12
|
+
|
|
13
|
+
# shellcheck source=bin/lib/config.sh
|
|
14
|
+
source "$ROOT/bin/lib/config.sh"
|
|
15
|
+
|
|
16
|
+
usage() {
|
|
17
|
+
echo 'usage: bash bin/person.sh {sync|onboard|set-name NAME|set-email EMAIL|show|backfill [--dry-run|--apply] [--include-removed]}' >&2
|
|
18
|
+
exit 2
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
authorize_identity() {
|
|
22
|
+
permission="$1"
|
|
23
|
+
resource="$2"
|
|
24
|
+
EGREGORE_ROOT="$ROOT" python3 -m egregore_runtime.identity_cli \
|
|
25
|
+
authorize-self "$permission" "$resource" >/dev/null
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
remote_config() {
|
|
29
|
+
api_url="${EGREGORE_API_URL:-$(_config_val api_url)}"
|
|
30
|
+
api_key="${EGREGORE_API_KEY:-$(_load_env_var EGREGORE_API_KEY)}"
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
sync_remote_identity() {
|
|
34
|
+
identity="$1"
|
|
35
|
+
remote_config
|
|
36
|
+
|
|
37
|
+
api_status="not-configured"
|
|
38
|
+
platform_user_id=""
|
|
39
|
+
if [ -n "$api_url" ] && [ -n "$api_key" ]; then
|
|
40
|
+
api_payload="$(printf '%s' "$identity" | jq '{
|
|
41
|
+
github_username,
|
|
42
|
+
github_id,
|
|
43
|
+
github_name,
|
|
44
|
+
github_aliases,
|
|
45
|
+
display_name,
|
|
46
|
+
email,
|
|
47
|
+
emails
|
|
48
|
+
}')"
|
|
49
|
+
api_result="$(curl -sf "${api_url}/api/user/ensure" \
|
|
50
|
+
-H "Authorization: Bearer ${api_key}" \
|
|
51
|
+
-H "Content-Type: application/json" \
|
|
52
|
+
-d "$api_payload" \
|
|
53
|
+
--max-time 10 2>/dev/null || true)"
|
|
54
|
+
api_status="$(printf '%s' "$api_result" | jq -r '.status // "failed"' 2>/dev/null || echo failed)"
|
|
55
|
+
platform_user_id="$(printf '%s' "$api_result" | jq -r '.user_id // empty' 2>/dev/null || true)"
|
|
56
|
+
if [ "$api_status" = "ok" ]; then
|
|
57
|
+
if ! printf '%s' "$api_result" | EGREGORE_ROOT="$ROOT" \
|
|
58
|
+
python3 -m egregore_runtime.identity_cli >/dev/null 2>&1; then
|
|
59
|
+
api_status="identity-reconcile-failed"
|
|
60
|
+
fi
|
|
61
|
+
fi
|
|
62
|
+
fi
|
|
63
|
+
|
|
64
|
+
# A removed membership is terminal until an admin explicitly re-invites
|
|
65
|
+
# the person. Never let startup recreate their graph membership.
|
|
66
|
+
if [ "$api_status" = "removed" ]; then
|
|
67
|
+
printf '%s' "$identity" | jq \
|
|
68
|
+
--arg platform_user_id "$platform_user_id" \
|
|
69
|
+
'. + {
|
|
70
|
+
status:"removed",
|
|
71
|
+
supabase:"removed",
|
|
72
|
+
graph:"skipped-removed",
|
|
73
|
+
platform_user_id:$platform_user_id,
|
|
74
|
+
merged_duplicates:0
|
|
75
|
+
}'
|
|
76
|
+
return 0
|
|
77
|
+
fi
|
|
78
|
+
|
|
79
|
+
params="$(printf '%s' "$identity" | jq --arg platformUserId "$platform_user_id" '{
|
|
80
|
+
personId:.person_id,
|
|
81
|
+
github:.github_username,
|
|
82
|
+
githubId:(if .github_id == null then "" else (.github_id|tostring) end),
|
|
83
|
+
fullName:.github_name,
|
|
84
|
+
displayName:.display_name,
|
|
85
|
+
primaryEmail:(.email // ""),
|
|
86
|
+
emails,
|
|
87
|
+
githubAliases:.github_aliases,
|
|
88
|
+
previousNames:.previous_names,
|
|
89
|
+
profilePath:.profile_path,
|
|
90
|
+
allowNameMatch:(
|
|
91
|
+
(.allow_name_match // false)
|
|
92
|
+
or (.source_profile // "") != ""
|
|
93
|
+
or ((.aliases_reconciled // []) | length) > 0
|
|
94
|
+
),
|
|
95
|
+
platformUserId:$platformUserId
|
|
96
|
+
}')"
|
|
97
|
+
|
|
98
|
+
graph_enabled="${EGREGORE_GRAPH_PROJECTION:-0}"
|
|
99
|
+
graph_status="disabled"
|
|
100
|
+
if [ "$graph_enabled" = "1" ]; then
|
|
101
|
+
graph_status="failed"
|
|
102
|
+
if graph_result="$(bash "$ROOT/bin/graph.sh" query "
|
|
103
|
+
OPTIONAL MATCH (legacy:Person)
|
|
104
|
+
WHERE NOT coalesce(legacy.kind, '') IN ['external', 'identity_alias']
|
|
105
|
+
AND coalesce(legacy.status, 'active') = 'active'
|
|
106
|
+
AND legacy.ingestRef IS NULL
|
|
107
|
+
AND (
|
|
108
|
+
legacy.personId = \$personId
|
|
109
|
+
OR (\$githubId <> '' AND coalesce(toString(legacy.githubId), '') = \$githubId)
|
|
110
|
+
OR toLower(coalesce(legacy.github, '')) = toLower(\$github)
|
|
111
|
+
OR toLower(coalesce(legacy.github, '')) IN
|
|
112
|
+
[alias IN \$githubAliases | toLower(alias)]
|
|
113
|
+
OR (
|
|
114
|
+
\$allowNameMatch
|
|
115
|
+
AND legacy.personId IS NULL
|
|
116
|
+
AND legacy.githubId IS NULL
|
|
117
|
+
AND (legacy.github IS NULL OR legacy.github = '')
|
|
118
|
+
AND toLower(coalesce(legacy.name, '')) = toLower(\$displayName)
|
|
119
|
+
)
|
|
120
|
+
)
|
|
121
|
+
WITH legacy
|
|
122
|
+
ORDER BY CASE
|
|
123
|
+
WHEN legacy.personId = \$personId THEN 0
|
|
124
|
+
WHEN \$githubId <> '' AND coalesce(toString(legacy.githubId), '') = \$githubId THEN 1
|
|
125
|
+
WHEN toLower(coalesce(legacy.github, '')) = toLower(\$github) THEN 2
|
|
126
|
+
ELSE 3
|
|
127
|
+
END
|
|
128
|
+
WITH head(collect(legacy)) AS legacy
|
|
129
|
+
FOREACH (_ IN CASE WHEN legacy IS NULL THEN [] ELSE [1] END |
|
|
130
|
+
SET legacy.personId = \$personId
|
|
131
|
+
)
|
|
132
|
+
MERGE (p:Person {personId: \$personId})
|
|
133
|
+
ON CREATE SET p.joined = date()
|
|
134
|
+
SET p.github = \$github,
|
|
135
|
+
p.githubId = CASE WHEN \$githubId = '' THEN p.githubId ELSE \$githubId END,
|
|
136
|
+
p.kind = 'member',
|
|
137
|
+
p.org = \$_org,
|
|
138
|
+
p.status = 'active',
|
|
139
|
+
p.removedAt = null,
|
|
140
|
+
p.identityStatus = CASE WHEN \$githubId = '' THEN 'provisional' ELSE 'verified' END,
|
|
141
|
+
p.platformUserId = CASE WHEN \$platformUserId = '' THEN p.platformUserId ELSE \$platformUserId END,
|
|
142
|
+
p.name = \$displayName,
|
|
143
|
+
p.displayName = \$displayName,
|
|
144
|
+
p.fullName = \$fullName,
|
|
145
|
+
p.email = CASE WHEN \$primaryEmail = '' THEN p.email ELSE \$primaryEmail END,
|
|
146
|
+
p.emails = reduce(acc = coalesce(p.emails, []), value IN \$emails |
|
|
147
|
+
CASE WHEN value IN acc THEN acc ELSE acc + value END),
|
|
148
|
+
p.githubAliases = reduce(acc = coalesce(p.githubAliases, []), value IN \$githubAliases |
|
|
149
|
+
CASE WHEN value IN acc THEN acc ELSE acc + value END),
|
|
150
|
+
p.previousNames = reduce(acc = coalesce(p.previousNames, []), value IN \$previousNames |
|
|
151
|
+
CASE WHEN value IN acc THEN acc ELSE acc + value END),
|
|
152
|
+
p.profilePath = \$profilePath,
|
|
153
|
+
p.identityVersion = 1,
|
|
154
|
+
p.identityUpdatedAt = datetime()
|
|
155
|
+
WITH p
|
|
156
|
+
MATCH (o:Org {id: \$_org})
|
|
157
|
+
MERGE (p)-[:MEMBER_OF]->(o)
|
|
158
|
+
RETURN p.personId AS personId
|
|
159
|
+
" "$params" 2>/dev/null)"; then
|
|
160
|
+
if printf '%s' "$graph_result" | jq -e \
|
|
161
|
+
--arg personId "$(printf '%s' "$identity" | jq -r .person_id)" \
|
|
162
|
+
'.values[0][0] == $personId' >/dev/null 2>&1; then
|
|
163
|
+
graph_status="synced"
|
|
164
|
+
fi
|
|
165
|
+
fi
|
|
166
|
+
fi
|
|
167
|
+
|
|
168
|
+
merged_duplicates=0
|
|
169
|
+
if [ "$graph_status" = "synced" ]; then
|
|
170
|
+
duplicates="$(bash "$ROOT/bin/graph.sh" query "
|
|
171
|
+
MATCH (real:Person {personId: \$personId})
|
|
172
|
+
MATCH (duplicate:Person)
|
|
173
|
+
WHERE duplicate <> real AND (
|
|
174
|
+
duplicate.personId = \$personId
|
|
175
|
+
OR (\$githubId <> '' AND coalesce(toString(duplicate.githubId), '') = \$githubId)
|
|
176
|
+
OR toLower(coalesce(duplicate.github, '')) = toLower(\$github)
|
|
177
|
+
OR toLower(coalesce(duplicate.github, '')) IN \$githubAliases
|
|
178
|
+
OR (
|
|
179
|
+
duplicate.githubId IS NULL
|
|
180
|
+
AND duplicate.personId IS NULL
|
|
181
|
+
AND (duplicate.github IS NULL OR duplicate.github = '')
|
|
182
|
+
AND any(email IN coalesce(duplicate.emails, []) WHERE email IN \$emails)
|
|
183
|
+
)
|
|
184
|
+
OR (
|
|
185
|
+
\$allowNameMatch
|
|
186
|
+
AND
|
|
187
|
+
(duplicate.github IS NULL OR duplicate.github = '')
|
|
188
|
+
AND duplicate.personId IS NULL
|
|
189
|
+
AND toLower(coalesce(duplicate.name, '')) = toLower(\$displayName)
|
|
190
|
+
)
|
|
191
|
+
)
|
|
192
|
+
AND NOT coalesce(duplicate.kind, '') IN ['external', 'identity_alias']
|
|
193
|
+
AND coalesce(duplicate.status, 'active') = 'active'
|
|
194
|
+
AND duplicate.ingestRef IS NULL
|
|
195
|
+
RETURN DISTINCT coalesce(duplicate.github, duplicate.name) AS ref
|
|
196
|
+
" "$params" 2>/dev/null || echo '{"values":[]}')"
|
|
197
|
+
while IFS= read -r duplicate; do
|
|
198
|
+
[ -n "$duplicate" ] || continue
|
|
199
|
+
if bash "$ROOT/bin/graph-op.sh" merge-person "$(printf '%s' "$identity" | jq -r .person_id)" \
|
|
200
|
+
"$duplicate" >/dev/null 2>&1; then
|
|
201
|
+
merged_duplicates=$((merged_duplicates + 1))
|
|
202
|
+
fi
|
|
203
|
+
done < <(printf '%s' "$duplicates" | jq -r '.values[]?[0] // empty')
|
|
204
|
+
fi
|
|
205
|
+
|
|
206
|
+
status="synced"
|
|
207
|
+
[ "$api_status" = "ok" ] || status="partial"
|
|
208
|
+
if [ "$graph_enabled" = "1" ] && [ "$graph_status" != "synced" ]; then
|
|
209
|
+
status="partial"
|
|
210
|
+
fi
|
|
211
|
+
printf '%s' "$identity" | jq \
|
|
212
|
+
--arg status "$status" \
|
|
213
|
+
--arg supabase "$api_status" \
|
|
214
|
+
--arg graph "$graph_status" \
|
|
215
|
+
--arg platform_user_id "$platform_user_id" \
|
|
216
|
+
--argjson merged_duplicates "$merged_duplicates" \
|
|
217
|
+
'. + {
|
|
218
|
+
status:$status,
|
|
219
|
+
supabase:$supabase,
|
|
220
|
+
graph:$graph,
|
|
221
|
+
platform_user_id:$platform_user_id,
|
|
222
|
+
merged_duplicates:$merged_duplicates
|
|
223
|
+
}'
|
|
224
|
+
}
|
|
225
|
+
|
|
226
|
+
backfill_people() {
|
|
227
|
+
mode="dry-run"
|
|
228
|
+
include_removed="false"
|
|
229
|
+
shift
|
|
230
|
+
while [ "$#" -gt 0 ]; do
|
|
231
|
+
case "$1" in
|
|
232
|
+
--dry-run) mode="dry-run" ;;
|
|
233
|
+
--apply) mode="apply" ;;
|
|
234
|
+
--include-removed) include_removed="true" ;;
|
|
235
|
+
*) usage ;;
|
|
236
|
+
esac
|
|
237
|
+
shift
|
|
238
|
+
done
|
|
239
|
+
|
|
240
|
+
if [ "$(_detect_mode)" = "local" ]; then
|
|
241
|
+
jq -n '{status:"unavailable",reason:"person backfill requires the hosted member roster in this configuration"}'
|
|
242
|
+
return 1
|
|
243
|
+
fi
|
|
244
|
+
command -v gh >/dev/null 2>&1 || {
|
|
245
|
+
jq -n '{status:"error",error:"GitHub CLI is required to resolve stable user ids"}'
|
|
246
|
+
return 1
|
|
247
|
+
}
|
|
248
|
+
|
|
249
|
+
remote_config
|
|
250
|
+
if [ -z "$api_url" ] || [ -z "$api_key" ]; then
|
|
251
|
+
jq -n '{status:"error",error:"connected API configuration is incomplete"}'
|
|
252
|
+
return 1
|
|
253
|
+
fi
|
|
254
|
+
org_slug="$(_config_val slug)"
|
|
255
|
+
members_result="$(curl -sf "${api_url}/api/org/${org_slug}/members?include_removed=true" \
|
|
256
|
+
-H "Authorization: Bearer ${api_key}" \
|
|
257
|
+
--max-time 20 2>/dev/null || true)"
|
|
258
|
+
if ! printf '%s' "$members_result" | jq -e '.members | type == "array"' >/dev/null 2>&1; then
|
|
259
|
+
jq -n '{status:"error",error:"could not load the hosted member roster"}'
|
|
260
|
+
return 1
|
|
261
|
+
fi
|
|
262
|
+
if ! printf '%s' "$members_result" | jq -e \
|
|
263
|
+
'.members | length == 0 or all(has("github_id") and has("github_aliases"))' \
|
|
264
|
+
>/dev/null 2>&1; then
|
|
265
|
+
jq -n '{status:"blocked",error:"the hosted API is still using the pre-identity member contract; deploy it before backfilling"}'
|
|
266
|
+
return 1
|
|
267
|
+
fi
|
|
268
|
+
|
|
269
|
+
results='[]'
|
|
270
|
+
excluded_removed=0
|
|
271
|
+
while IFS= read -r member; do
|
|
272
|
+
[ -n "$member" ] || continue
|
|
273
|
+
member_status="$(printf '%s' "$member" | jq -r '.status // "active"')"
|
|
274
|
+
if [ "$member_status" != "active" ] && [ "$include_removed" != "true" ]; then
|
|
275
|
+
excluded_removed=$((excluded_removed + 1))
|
|
276
|
+
continue
|
|
277
|
+
fi
|
|
278
|
+
|
|
279
|
+
previous_github="$(printf '%s' "$member" | jq -r '.github_username // empty')"
|
|
280
|
+
if ! printf '%s' "$previous_github" | grep -Eq '^[A-Za-z0-9-]{1,39}$'; then
|
|
281
|
+
item="$(jq -n --arg github "$previous_github" '{
|
|
282
|
+
github_username:$github,status:"skipped",reason:"invalid GitHub login"
|
|
283
|
+
}')"
|
|
284
|
+
results="$(printf '%s' "$results" | jq --argjson item "$item" '. + [$item]')"
|
|
285
|
+
continue
|
|
286
|
+
fi
|
|
287
|
+
|
|
288
|
+
github_result="$(gh api "users/${previous_github}" \
|
|
289
|
+
--jq '{login,id,name,email}' 2>/dev/null || true)"
|
|
290
|
+
if ! printf '%s' "$github_result" | jq -e \
|
|
291
|
+
'.login and (.id | type == "number")' >/dev/null 2>&1; then
|
|
292
|
+
item="$(jq -n --arg github "$previous_github" '{
|
|
293
|
+
github_username:$github,status:"unresolved",reason:"GitHub identity could not be resolved"
|
|
294
|
+
}')"
|
|
295
|
+
results="$(printf '%s' "$results" | jq --argjson item "$item" '. + [$item]')"
|
|
296
|
+
continue
|
|
297
|
+
fi
|
|
298
|
+
|
|
299
|
+
github="$(printf '%s' "$github_result" | jq -r .login)"
|
|
300
|
+
github_id="$(printf '%s' "$github_result" | jq -r .id)"
|
|
301
|
+
github_name="$(printf '%s' "$github_result" | jq -r '.name // empty')"
|
|
302
|
+
public_email="$(printf '%s' "$github_result" | jq -r '.email // empty')"
|
|
303
|
+
display_name="$(printf '%s' "$member" | jq -r \
|
|
304
|
+
--arg githubName "$github_name" --arg github "$github" \
|
|
305
|
+
'.display_name // (if $githubName != "" then $githubName else $github end)')"
|
|
306
|
+
role="$(printf '%s' "$member" | jq -r '.member_role // .role // "Member"')"
|
|
307
|
+
joined="$(printf '%s' "$member" | jq -r '.joined_at // empty' | cut -c1-10)"
|
|
308
|
+
aliases="$(printf '%s' "$member" | jq -r \
|
|
309
|
+
--arg old "$previous_github" --arg current "$github" '
|
|
310
|
+
((.github_aliases // []) + (if ($old|ascii_downcase) != ($current|ascii_downcase) then [$old] else [] end))
|
|
311
|
+
| map(select(type == "string" and length > 0)) | unique | join(",")
|
|
312
|
+
')"
|
|
313
|
+
emails="$(printf '%s' "$member" | jq -r \
|
|
314
|
+
--arg public "$public_email" '
|
|
315
|
+
((.emails // []) + [(.primary_email // ""), $public])
|
|
316
|
+
| map(select(type == "string" and length > 0)) | unique | join(",")
|
|
317
|
+
')"
|
|
318
|
+
|
|
319
|
+
profile_args=(
|
|
320
|
+
sync-profile
|
|
321
|
+
--github "$github"
|
|
322
|
+
--github-id "$github_id"
|
|
323
|
+
--github-name "$github_name"
|
|
324
|
+
--display-name "$display_name"
|
|
325
|
+
--previous-github "$previous_github"
|
|
326
|
+
--github-aliases "$aliases"
|
|
327
|
+
--emails "$emails"
|
|
328
|
+
--role "$role"
|
|
329
|
+
--joined "$joined"
|
|
330
|
+
)
|
|
331
|
+
[ "$mode" = "apply" ] || profile_args+=(--dry-run)
|
|
332
|
+
if ! identity="$(python3 "$PERSON_PY" "${profile_args[@]}")"; then
|
|
333
|
+
item="$(jq -n --arg github "$github" '{
|
|
334
|
+
github_username:$github,status:"skipped",reason:"profile reconciliation failed"
|
|
335
|
+
}')"
|
|
336
|
+
results="$(printf '%s' "$results" | jq --argjson item "$item" '. + [$item]')"
|
|
337
|
+
continue
|
|
338
|
+
fi
|
|
339
|
+
roster_name_matches="$(printf '%s' "$members_result" | jq \
|
|
340
|
+
--arg displayName "$display_name" '
|
|
341
|
+
[.members[]
|
|
342
|
+
| (.display_name // "")
|
|
343
|
+
| select(length > 0)
|
|
344
|
+
| ascii_downcase
|
|
345
|
+
| select(. == ($displayName | ascii_downcase))]
|
|
346
|
+
| length
|
|
347
|
+
')"
|
|
348
|
+
allow_name_match="false"
|
|
349
|
+
[ "$roster_name_matches" -eq 1 ] && allow_name_match="true"
|
|
350
|
+
identity="$(printf '%s' "$identity" | jq \
|
|
351
|
+
--argjson allowNameMatch "$allow_name_match" \
|
|
352
|
+
'.allow_name_match = $allowNameMatch')"
|
|
353
|
+
|
|
354
|
+
if [ "$mode" = "apply" ]; then
|
|
355
|
+
synced="$(sync_remote_identity "$identity")"
|
|
356
|
+
report="$(printf '%s' "$synced" | jq 'del(.email,.emails,.allow_name_match)')"
|
|
357
|
+
else
|
|
358
|
+
report="$(printf '%s' "$identity" | jq \
|
|
359
|
+
'. + {status:"planned"} | del(.email,.emails,.allow_name_match)')"
|
|
360
|
+
fi
|
|
361
|
+
results="$(printf '%s' "$results" | jq --argjson item "$report" '. + [$item]')"
|
|
362
|
+
done < <(printf '%s' "$members_result" | jq -c '.members[]')
|
|
363
|
+
|
|
364
|
+
printf '%s' "$results" | jq \
|
|
365
|
+
--arg mode "$mode" \
|
|
366
|
+
--arg org "$org_slug" \
|
|
367
|
+
--argjson excluded_removed "$excluded_removed" '
|
|
368
|
+
{
|
|
369
|
+
status:(if any(.[]; .status == "partial") then "partial" else "ok" end),
|
|
370
|
+
mode:$mode,
|
|
371
|
+
org:$org,
|
|
372
|
+
summary:{
|
|
373
|
+
considered:length,
|
|
374
|
+
planned_or_synced:[.[] | select(.status == "planned" or .status == "synced")]|length,
|
|
375
|
+
partial:[.[] | select(.status == "partial")]|length,
|
|
376
|
+
unresolved:[.[] | select(.status == "unresolved")]|length,
|
|
377
|
+
skipped:[.[] | select(.status == "skipped")]|length,
|
|
378
|
+
excluded_removed:$excluded_removed
|
|
379
|
+
},
|
|
380
|
+
people:.
|
|
381
|
+
}'
|
|
382
|
+
}
|
|
383
|
+
|
|
384
|
+
command="${1:-}"
|
|
385
|
+
[ -n "$command" ] || usage
|
|
386
|
+
|
|
387
|
+
if [ "$command" = "show" ]; then
|
|
388
|
+
authorize_identity read "identity:self"
|
|
389
|
+
jq '{
|
|
390
|
+
person_id,
|
|
391
|
+
display_name,
|
|
392
|
+
github_username,
|
|
393
|
+
github_id,
|
|
394
|
+
github_name,
|
|
395
|
+
email,
|
|
396
|
+
emails,
|
|
397
|
+
github_aliases,
|
|
398
|
+
previous_names,
|
|
399
|
+
identity_version
|
|
400
|
+
}' "$STATE"
|
|
401
|
+
exit 0
|
|
402
|
+
fi
|
|
403
|
+
|
|
404
|
+
if [ "$command" = "backfill" ]; then
|
|
405
|
+
authorize_identity administer "identity:roster"
|
|
406
|
+
backfill_people "$@"
|
|
407
|
+
exit $?
|
|
408
|
+
fi
|
|
409
|
+
|
|
410
|
+
display_args=()
|
|
411
|
+
email_args=()
|
|
412
|
+
onboard_args=()
|
|
413
|
+
case "$command" in
|
|
414
|
+
sync) ;;
|
|
415
|
+
onboard) onboard_args=(--onboarded) ;;
|
|
416
|
+
set-name)
|
|
417
|
+
name="${2:-}"
|
|
418
|
+
[ -n "$name" ] || usage
|
|
419
|
+
if [ "${#name}" -gt 60 ] || ! printf '%s' "$name" | grep -Eq "^[[:alnum:]À-ž .'-]+$"; then
|
|
420
|
+
echo '{"status":"error","error":"display name must be 1-60 name characters"}'
|
|
421
|
+
exit 2
|
|
422
|
+
fi
|
|
423
|
+
display_args=(--display-name "$name")
|
|
424
|
+
;;
|
|
425
|
+
set-email)
|
|
426
|
+
email="${2:-}"
|
|
427
|
+
[ -n "$email" ] || usage
|
|
428
|
+
if [ "${#email}" -gt 254 ] || ! printf '%s' "$email" | grep -Eq '^[^[:space:]@]+@[^[:space:]@]+\.[^[:space:]@]+$'; then
|
|
429
|
+
echo '{"status":"error","error":"email must be a valid address"}'
|
|
430
|
+
exit 2
|
|
431
|
+
fi
|
|
432
|
+
email_args=(--email "$email")
|
|
433
|
+
;;
|
|
434
|
+
*) usage ;;
|
|
435
|
+
esac
|
|
436
|
+
|
|
437
|
+
# Bootstrap reconciliation is allowed to establish the first ActorContext;
|
|
438
|
+
# every explicit self-service mutation must authorize before provider lookup,
|
|
439
|
+
# canonical profile writes, control-plane reconciliation, or projection.
|
|
440
|
+
if [ "$command" = "set-name" ] || [ "$command" = "set-email" ]; then
|
|
441
|
+
authorize_identity administer "identity:self"
|
|
442
|
+
fi
|
|
443
|
+
|
|
444
|
+
github_args=()
|
|
445
|
+
state_github="$(jq -r '.github_username // empty' "$STATE" 2>/dev/null)"
|
|
446
|
+
if command -v gh >/dev/null 2>&1; then
|
|
447
|
+
gh_identity="$(gh api user --jq '{login,id,name,email}' 2>/dev/null || true)"
|
|
448
|
+
gh_login="$(printf '%s' "$gh_identity" | jq -r '.login // empty' 2>/dev/null)"
|
|
449
|
+
gh_id="$(printf '%s' "$gh_identity" | jq -r '.id // empty' 2>/dev/null)"
|
|
450
|
+
state_github_id="$(jq -r '.github_id // empty' "$STATE" 2>/dev/null)"
|
|
451
|
+
gh_login_lc="$(printf '%s' "$gh_login" | tr '[:upper:]' '[:lower:]')"
|
|
452
|
+
state_github_lc="$(printf '%s' "$state_github" | tr '[:upper:]' '[:lower:]')"
|
|
453
|
+
if [ -n "$gh_login" ] && {
|
|
454
|
+
[ -z "$state_github" ] ||
|
|
455
|
+
[ "$gh_login_lc" = "$state_github_lc" ] ||
|
|
456
|
+
{ [ -n "$gh_id" ] && [ -n "$state_github_id" ] && [ "$gh_id" = "$state_github_id" ]; }
|
|
457
|
+
}; then
|
|
458
|
+
github_args=(--github "$gh_login")
|
|
459
|
+
gh_email="$(printf '%s' "$gh_identity" | jq -r '.email // empty')"
|
|
460
|
+
[ -z "$gh_id" ] || github_args+=(--github-id "$gh_id")
|
|
461
|
+
[ -z "$gh_email" ] || github_args+=(--email "$gh_email")
|
|
462
|
+
fi
|
|
463
|
+
fi
|
|
464
|
+
|
|
465
|
+
if [ "$(jq -r '.onboarding_complete // false' "$STATE" 2>/dev/null)" = "true" ]; then
|
|
466
|
+
onboard_args=(--onboarded)
|
|
467
|
+
fi
|
|
468
|
+
# macOS still ships Bash 3.2, where expanding an empty array under `set -u`
|
|
469
|
+
# raises "unbound variable". Disable nounset only for this argument expansion;
|
|
470
|
+
# every value remains passed as a separately quoted argument.
|
|
471
|
+
set +u
|
|
472
|
+
identity="$(python3 "$PERSON_PY" sync-local \
|
|
473
|
+
"${display_args[@]}" "${github_args[@]}" "${email_args[@]}" "${onboard_args[@]}")"
|
|
474
|
+
set -u
|
|
475
|
+
|
|
476
|
+
if [ "$(_detect_mode)" = "local" ]; then
|
|
477
|
+
printf '%s' "$identity" | jq '. + {status:"synced-local",supabase:"unavailable",graph:"unavailable"}'
|
|
478
|
+
exit 0
|
|
479
|
+
fi
|
|
480
|
+
|
|
481
|
+
sync_remote_identity "$identity"
|
|
@@ -0,0 +1,140 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
// Derive Pi's project-local system appendix from the generated Codex protocol.
|
|
3
|
+
// CLAUDE.md remains canonical: CLAUDE.md -> AGENTS.md -> .pi/APPEND_SYSTEM.md.
|
|
4
|
+
// The second hop deliberately reuses the reviewed shell-runtime translation,
|
|
5
|
+
// then adapts only the harness surfaces that differ between Codex and Pi.
|
|
6
|
+
|
|
7
|
+
import crypto from "node:crypto";
|
|
8
|
+
import fs from "node:fs";
|
|
9
|
+
import path from "node:path";
|
|
10
|
+
import { fileURLToPath } from "node:url";
|
|
11
|
+
|
|
12
|
+
const ROOT = path.resolve(path.dirname(fileURLToPath(import.meta.url)), "..");
|
|
13
|
+
const SOURCE = path.join(ROOT, "AGENTS.md");
|
|
14
|
+
const OUTPUT = path.join(ROOT, ".pi", "APPEND_SYSTEM.md");
|
|
15
|
+
const MANIFEST = path.join(ROOT, ".pi", "spec-manifest.json");
|
|
16
|
+
const CODEX_BEGIN = "<!-- BEGIN GENERATED EGREGORE CODEX SPEC";
|
|
17
|
+
const CODEX_END = "<!-- END GENERATED EGREGORE CODEX SPEC -->";
|
|
18
|
+
|
|
19
|
+
function hash(value) {
|
|
20
|
+
return crypto.createHash("sha256").update(value).digest("hex").slice(0, 12);
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
function extractSpec(source) {
|
|
24
|
+
const begin = source.indexOf(CODEX_BEGIN);
|
|
25
|
+
const contentStart = source.indexOf("\n", begin);
|
|
26
|
+
const end = source.indexOf(CODEX_END, contentStart);
|
|
27
|
+
if (begin < 0 || contentStart < 0 || end < 0) {
|
|
28
|
+
throw new Error("AGENTS.md does not contain the generated Codex spec");
|
|
29
|
+
}
|
|
30
|
+
return source.slice(contentStart + 1, end).trim();
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
function replaceSection(markdown, heading, body) {
|
|
34
|
+
const marker = `## ${heading}`;
|
|
35
|
+
const start = markdown.indexOf(marker);
|
|
36
|
+
if (start < 0) throw new Error(`missing section in AGENTS.md: ${heading}`);
|
|
37
|
+
const rest = markdown.slice(start + marker.length);
|
|
38
|
+
const boundary = rest.search(/\n\n---\n\n## /);
|
|
39
|
+
const end = boundary < 0 ? markdown.length : start + marker.length + boundary;
|
|
40
|
+
return `${markdown.slice(0, start)}${marker}\n\n${body}${markdown.slice(end)}`;
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
// Keep an inherited section and put runtime-specific framing in front of it.
|
|
44
|
+
// Command Awareness is the case that matters: the canonical category rows and
|
|
45
|
+
// disambiguation map live in CLAUDE.md, and a full replace here silently
|
|
46
|
+
// shipped a truncated copy that drifted for months. The Codex spec opens the
|
|
47
|
+
// section with its own skills-not-slash-commands paragraph, which is wrong for
|
|
48
|
+
// a runtime that does have slash commands, so that one paragraph is dropped.
|
|
49
|
+
function prependToSection(markdown, heading, body, dropLeadParagraphStartingWith) {
|
|
50
|
+
const marker = `## ${heading}`;
|
|
51
|
+
const start = markdown.indexOf(marker);
|
|
52
|
+
if (start < 0) throw new Error(`missing section in AGENTS.md: ${heading}`);
|
|
53
|
+
const rest = markdown.slice(start + marker.length);
|
|
54
|
+
const boundary = rest.search(/\n\n---\n\n## /);
|
|
55
|
+
const end = boundary < 0 ? markdown.length : start + marker.length + boundary;
|
|
56
|
+
let inherited = markdown.slice(start + marker.length, end).trim();
|
|
57
|
+
if (dropLeadParagraphStartingWith) {
|
|
58
|
+
if (!inherited.startsWith(dropLeadParagraphStartingWith)) {
|
|
59
|
+
throw new Error(`pi/prime-render-spec: "${heading}" no longer opens with "${dropLeadParagraphStartingWith}" — the Codex wording moved; update this adaptation`);
|
|
60
|
+
}
|
|
61
|
+
inherited = inherited.slice(inherited.indexOf("\n\n") + 2).trim();
|
|
62
|
+
}
|
|
63
|
+
return replaceSection(markdown, heading, `${body}\n\n${inherited}`);
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
const CODEX_COMMAND_LEAD = "Codex reserves leading";
|
|
67
|
+
|
|
68
|
+
function adapt(sourceSpec) {
|
|
69
|
+
// Anchored replacements: every `from` string MUST exist in the generated
|
|
70
|
+
// Codex spec. A missing anchor once no-opped silently (the tool_call gate
|
|
71
|
+
// wording vanished from this file for a whole PR cycle before a test caught
|
|
72
|
+
// it) — now it fails the render loudly so the anchor gets updated alongside
|
|
73
|
+
// the Codex text that moved.
|
|
74
|
+
const ANCHORED = [
|
|
75
|
+
["Egregore on Codex", "Egregore on Pi"],
|
|
76
|
+
["Codex-native", "Pi-native"],
|
|
77
|
+
["Codex sessions", "Pi sessions"],
|
|
78
|
+
["On Codex", "On Pi"],
|
|
79
|
+
["Codex has no", "Pi has no built-in"],
|
|
80
|
+
["bin/codex-session-start.sh", "bin/pi-session-start.sh"],
|
|
81
|
+
[".codex/hooks/branch-guard.js", ".pi/extensions/egregore.ts"],
|
|
82
|
+
["PreToolUse hook (launcher `--enable hooks`)", "`tool_call` gate (loaded after Pi project trust)"],
|
|
83
|
+
["If this Codex build does not support hooks", "If Pi project resources are disabled"],
|
|
84
|
+
["change permissions in `.claude/settings.json` anytime", "review or disable project resources in `.pi/` anytime"],
|
|
85
|
+
];
|
|
86
|
+
let text = sourceSpec;
|
|
87
|
+
for (const [from, to] of ANCHORED) {
|
|
88
|
+
if (!text.includes(from)) {
|
|
89
|
+
throw new Error(`pi-render-spec: anchor not found in generated Codex spec: "${from}" — the Codex wording moved; update this replacement`);
|
|
90
|
+
}
|
|
91
|
+
text = text.replaceAll(from, to);
|
|
92
|
+
}
|
|
93
|
+
text = text
|
|
94
|
+
.replace(/`\$([a-z][a-z0-9-]*)/g, "`/$1")
|
|
95
|
+
.replace(/\$([a-z][a-z0-9-]*)/g, "/$1");
|
|
96
|
+
|
|
97
|
+
text = replaceSection(text, "Egregore on Pi", `You are Pi running inside Egregore — a shared intelligence layer for organizations using AI coding agents. You operate through Git-based shared memory, project-local Pi resources, Egregore skills, and conventions that accumulate knowledge across sessions and people. You are not a tool. You are a participant.
|
|
98
|
+
|
|
99
|
+
This appendix is generated from the reviewed shell-runtime translation of \`CLAUDE.md\`, the behavioral source of truth. Pi loads it through \`.pi/APPEND_SYSTEM.md\` after the launcher grants project trust for this run. Egregore workflows are shared from \`.codex/skills/\` using Pi's documented cross-harness skill support and exposed as familiar slash commands by \`.pi/extensions/egregore.ts\`.`);
|
|
100
|
+
|
|
101
|
+
text = replaceSection(text, "On Launch — MANDATORY FIRST ACTION", `The project-local Pi extension renders the Egregore startup card (identity, handoffs, team activity) inside Pi via \`bin/pi-session-start.sh\`. This works for direct \`pi\` launches and launcher-managed sessions. Do not rerun startup checks and do not narrate startup. The card ends with **"What are you working on?"** — that question is already on screen; treat the user's first message as the answer to it. To re-show the card outside Pi, run \`bash bin/pi-session-start.sh --card\`.`);
|
|
102
|
+
|
|
103
|
+
text = prependToSection(text, "Command Awareness", `Egregore workflows are available as Pi slash commands such as \`/activity\`, \`/handoff\`, \`/save\`, and \`/view\`. They are registered from the shared skill inventory by \`.pi/extensions/egregore.ts\`. Pi also exposes the underlying Agent Skills as \`/skill:name\`, and natural-language requests work normally. \`/save\` is the user-facing abstraction for committing, pushing, opening or reusing pull requests, and syncing memory — never make users manage the git workflow by hand.
|
|
104
|
+
|
|
105
|
+
Read the selected skill's \`SKILL.md\` completely before acting. Codex wording inside the shared portable skills means the shell-capable runtime adapter; in Pi, run referenced \`bin/\` scripts directly, use ordinary Pi shell/network access, ignore Codex approval-channel wording, and render compact numbered questions when no Pi UI question surface is available.`, CODEX_COMMAND_LEAD);
|
|
106
|
+
|
|
107
|
+
return `# Egregore on Pi\n\nThis file is generated by \`bin/pi-render-spec.mjs\`; do not edit it by hand.\n\n${text}\n`;
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
const check = process.argv.includes("--check");
|
|
111
|
+
const source = fs.readFileSync(SOURCE, "utf8");
|
|
112
|
+
const sourceSpec = extractSpec(source);
|
|
113
|
+
const rendered = adapt(sourceSpec);
|
|
114
|
+
const manifest = `${JSON.stringify({
|
|
115
|
+
generatedBy: "bin/pi-render-spec.mjs",
|
|
116
|
+
source: "AGENTS.md generated Codex spec",
|
|
117
|
+
sourceHash: hash(sourceSpec),
|
|
118
|
+
outputHash: hash(rendered),
|
|
119
|
+
adaptations: [
|
|
120
|
+
"Pi project trust and APPEND_SYSTEM delivery",
|
|
121
|
+
"Pi tool_call branch gate",
|
|
122
|
+
"Pi slash-command extension over shared portable skills",
|
|
123
|
+
"plain-text question fallback and direct shell/network execution",
|
|
124
|
+
],
|
|
125
|
+
}, null, 2)}\n`;
|
|
126
|
+
|
|
127
|
+
if (check) {
|
|
128
|
+
const currentOutput = fs.existsSync(OUTPUT) ? fs.readFileSync(OUTPUT, "utf8") : "";
|
|
129
|
+
const currentManifest = fs.existsSync(MANIFEST) ? fs.readFileSync(MANIFEST, "utf8") : "";
|
|
130
|
+
if (currentOutput !== rendered || currentManifest !== manifest) {
|
|
131
|
+
console.error("pi spec out of date — run: bash bin/node-run.sh bin/pi-render-spec.mjs");
|
|
132
|
+
process.exit(1);
|
|
133
|
+
}
|
|
134
|
+
console.log("pi spec up to date");
|
|
135
|
+
} else {
|
|
136
|
+
fs.mkdirSync(path.dirname(OUTPUT), { recursive: true });
|
|
137
|
+
fs.writeFileSync(OUTPUT, rendered);
|
|
138
|
+
fs.writeFileSync(MANIFEST, manifest);
|
|
139
|
+
console.log(`pi spec rendered: .pi/APPEND_SYSTEM.md (${Buffer.byteLength(rendered)} bytes)`);
|
|
140
|
+
}
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
#!/usr/bin/env bash
|
|
2
|
+
# Post-update migrations for Egregore framework.
|
|
3
|
+
#
|
|
4
|
+
# This script is synced from upstream on every /update. All migration
|
|
5
|
+
# logic lives here — not in the /update skill itself. This avoids the
|
|
6
|
+
# chicken-and-egg problem: the dumb syncer pulls this script, then
|
|
7
|
+
# this script handles whatever needs to happen.
|
|
8
|
+
#
|
|
9
|
+
# Migrations must be idempotent — they run on every update.
|
|
10
|
+
|
|
11
|
+
set -euo pipefail
|
|
12
|
+
|
|
13
|
+
MIGRATED=0
|
|
14
|
+
|
|
15
|
+
# --- Migration: commands → skills (CC 2.0+) ---
|
|
16
|
+
# CC 2.0 dropped .claude/commands/ support. If skills exist (synced from
|
|
17
|
+
# upstream) and commands still exist locally, remove commands to prevent
|
|
18
|
+
# duplicate entries in the slash menu.
|
|
19
|
+
if [ -d ".claude/skills" ] && [ -d ".claude/commands" ]; then
|
|
20
|
+
CC_MAJOR=$(claude --version 2>/dev/null | grep -oE '^[0-9]+' || echo "0")
|
|
21
|
+
if [ "${CC_MAJOR:-0}" -ge 2 ]; then
|
|
22
|
+
git rm -r .claude/commands/ 2>/dev/null || rm -rf .claude/commands/
|
|
23
|
+
echo " ✓ Removed .claude/commands/ (migrated to skills)"
|
|
24
|
+
MIGRATED=1
|
|
25
|
+
fi
|
|
26
|
+
fi
|
|
27
|
+
|
|
28
|
+
# --- Future migrations go here ---
|
|
29
|
+
# Each migration should:
|
|
30
|
+
# 1. Check if it needs to run (idempotent guard)
|
|
31
|
+
# 2. Do the work
|
|
32
|
+
# 3. Echo a status line
|
|
33
|
+
# 4. Set MIGRATED=1
|
|
34
|
+
|
|
35
|
+
if [ "$MIGRATED" -eq 0 ]; then
|
|
36
|
+
echo " ✓ No migrations needed"
|
|
37
|
+
fi
|