total-recall-brain 3.45.0 → 3.46.1
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/bin/total-recall.mjs +7 -2
- package/frontend/dist/assets/index-BRYE1jmv.css +1 -0
- package/frontend/dist/assets/index-D1goIPjC.js +5598 -0
- package/frontend/dist/index.html +2 -2
- package/frontend/dist/sw.js +5 -4
- package/frontend/src/App.tsx +183 -236
- package/frontend/src/api/auth-inventory.ts +62 -0
- package/frontend/src/api/memory.ts +13 -8
- package/frontend/src/api/plugin-credentials.ts +23 -0
- package/frontend/src/api/plugins.ts +37 -53
- package/frontend/src/api/workspace-drawers.ts +97 -0
- package/frontend/src/components/BrainSelector.tsx +9 -3
- package/frontend/src/components/plugins/PluginPanel.tsx +83 -42
- package/frontend/src/components/plugins/PluginSettings.tsx +10 -20
- package/frontend/src/components/plugins/PluginWorkspace.tsx +367 -0
- package/frontend/src/components/plugins/ScopedPluginCommands.tsx +142 -0
- package/frontend/src/components/plugins/plugin-frame.ts +44 -33
- package/frontend/src/components/plugins/scoped-plugin-operations.ts +28 -0
- package/frontend/src/components/workspace/DrawerChat.tsx +110 -0
- package/frontend/src/components/workspace/DrawerLayout.tsx +196 -0
- package/frontend/src/components/workspace/DrawerMarkup.tsx +49 -0
- package/frontend/src/components/workspace/PluginChunkLibrary.tsx +92 -0
- package/frontend/src/components/workspace/PluginHome.tsx +76 -0
- package/frontend/src/components/workspace/WorkspaceDrawers.tsx +96 -0
- package/frontend/src/components/workspace/WorkspacePage.tsx +95 -0
- package/frontend/src/components/workspace/usePluginDesign.ts +38 -0
- package/frontend/src/index.css +409 -136
- package/frontend/src/pages/HelpPage.tsx +15 -46
- package/frontend/src/pages/MemoryPage.tsx +19 -36
- package/frontend/src/pages/SettingsPage.tsx +1 -1
- package/metadata.plugin.schema.json +53 -227
- package/package.json +1 -1
- package/scaffold/.agent/skills/plugin/SKILL.md +13 -11
- package/scaffold/.agent/skills/plugin/evals/README.md +14 -21
- package/scaffold/.agent/skills/plugin/evals/cases/01-fabricated-seed.mjs +15 -18
- package/scaffold/.agent/skills/plugin/evals/cases/02-reassuring-default.mjs +19 -24
- package/scaffold/.agent/skills/plugin/evals/cases/03-declared-template.mjs +12 -20
- package/scaffold/.agent/skills/plugin/evals/cases/04-home-collects-credential.mjs +35 -0
- package/scaffold/.agent/skills/plugin/evals/cases/05-host-leak-in-scaffold.mjs +8 -28
- package/scaffold/.agent/skills/plugin/evals/cases/06-correct-plugin.mjs +85 -47
- package/scaffold/.agent/skills/plugin/evals/run.mjs +17 -18
- package/scaffold/.agent/skills/plugin/prompts/05-credentials.md +4 -4
- package/scaffold/.agent/skills/plugin/prompts/07-scaffold.md +2 -2
- package/scaffold/.agent/skills/plugin/prompts/08-verify.md +4 -4
- package/scaffold/.agent/skills/plugin/references/anti-patterns.md +2 -2
- package/scaffold/.agent/skills/plugin/references/generative-home.md +38 -0
- package/scaffold/.agent/skills/plugin/references/scaffold.md +5 -5
- package/scaffold/.agent/skills/plugin/references/surfaces.md +13 -4
- package/scaffold/.agent/skills/plugin/scripts/record.mjs +75 -153
- package/scaffold/.agent/skills/plugin/subagents/plugin-reviewer.md +4 -4
- package/scaffold/.agent/skills/total-recall/plugins/auth/DESIGN.md +76 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/README.md +3 -1
- package/scaffold/.agent/skills/total-recall/plugins/auth/cli.mjs +20 -15
- package/scaffold/.agent/skills/total-recall/plugins/auth/package-lock.json +6 -6
- package/scaffold/.agent/skills/total-recall/plugins/auth/package.json +2 -1
- package/scaffold/.agent/skills/total-recall/plugins/auth/plugin.json +13 -51
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/chunks/access-overview.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/chunks/agent-login.md +20 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/chunks/baseline-audit.md +22 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/chunks/credential-repository-binding.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/chunks/credential-store-maintenance.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/chunks/dashboard-password.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/chunks/dashboard-sessions.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/chunks/endpoint-probe.md +23 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/chunks/google-sign-in.md +21 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/chunks/mesh-machines.md +16 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/chunks/passkey-enrollment.md +21 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/chunks/registered-brains.md +16 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/chunks/scoped-access-keys.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/chunks/secret-inventory.md +25 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/chunks/signing-key-rotation.md +22 -0
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/home.js +375 -0
- package/scaffold/.agent/skills/total-recall/plugins/automations/{ui/DESIGN.md → DESIGN.md} +32 -21
- package/scaffold/.agent/skills/total-recall/plugins/automations/adapters.mjs +17 -1
- package/scaffold/.agent/skills/total-recall/plugins/automations/cli.mjs +10 -1
- package/scaffold/.agent/skills/total-recall/plugins/automations/package-lock.json +6 -6
- package/scaffold/.agent/skills/total-recall/plugins/automations/package.json +4 -3
- package/scaffold/.agent/skills/total-recall/plugins/automations/plugin.json +11 -27
- package/scaffold/.agent/skills/total-recall/plugins/automations/ui/automations.js +2 -2
- package/scaffold/.agent/skills/total-recall/plugins/automations/ui/chunks/control-ledger.md +42 -0
- package/scaffold/.agent/skills/total-recall/plugins/automations/ui/chunks/local-inventory-triage.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/automations/ui/chunks/pending-control.md +39 -0
- package/scaffold/.agent/skills/total-recall/plugins/automations/ui/chunks/run-evidence.md +41 -0
- package/scaffold/.agent/skills/total-recall/plugins/automations/ui/chunks/schedule-vs-run-evidence.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/automations/ui/chunks/source-coverage.md +41 -0
- package/scaffold/.agent/skills/total-recall/plugins/automations/ui/{card.js → home.js} +32 -27
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/DESIGN.md +53 -0
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/cli.mjs +23 -0
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/commands/run-core.mjs +4 -2
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/core/check.mjs +4 -2
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/package-lock.json +6 -6
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/package.json +2 -1
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/plugin.json +40 -40
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/ui/chunks/config.md +15 -0
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/ui/chunks/detect.md +15 -0
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/ui/chunks/gate.md +15 -0
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/ui/chunks/init.md +15 -0
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/ui/chunks/report.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/ui/chunks/run.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/ui/chunks/snapshot.md +15 -0
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/ui/code-quality-report.mjs +55 -23
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/ui/home.mjs +214 -0
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/DESIGN.md +146 -0
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/package-lock.json +6 -6
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/package.json +2 -1
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/plugin.json +51 -34
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/src/command.mjs +1 -1
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/ui/chunks/create.md +35 -0
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/ui/chunks/history.md +35 -0
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/ui/chunks/library.md +49 -0
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/ui/chunks/list.md +42 -0
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/ui/chunks/promote.md +40 -0
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/ui/chunks/read.md +25 -0
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/ui/chunks/remove.md +26 -0
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/ui/chunks/rollback.md +26 -0
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/ui/chunks/show.md +53 -0
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/ui/chunks/status.md +40 -0
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/ui/chunks/test-path.md +38 -0
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/ui/chunks/test.md +46 -0
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/ui/chunks/update.md +32 -0
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/ui/home.js +533 -0
- package/scaffold/.agent/skills/total-recall/plugins/embeddings/DESIGN.md +110 -0
- package/scaffold/.agent/skills/total-recall/plugins/embeddings/package-lock.json +6 -6
- package/scaffold/.agent/skills/total-recall/plugins/embeddings/package.json +2 -1
- package/scaffold/.agent/skills/total-recall/plugins/embeddings/plugin.json +13 -10
- package/scaffold/.agent/skills/total-recall/plugins/embeddings/ui/chunks/benchmark.md +49 -0
- package/scaffold/.agent/skills/total-recall/plugins/embeddings/ui/chunks/coverage.md +53 -0
- package/scaffold/.agent/skills/total-recall/plugins/embeddings/ui/chunks/models.md +43 -0
- package/scaffold/.agent/skills/total-recall/plugins/embeddings/ui/chunks/pull.md +41 -0
- package/scaffold/.agent/skills/total-recall/plugins/embeddings/ui/chunks/status.md +59 -0
- package/scaffold/.agent/skills/total-recall/plugins/embeddings/ui/home.js +353 -0
- package/scaffold/.agent/skills/total-recall/plugins/git/DESIGN.md +31 -0
- package/scaffold/.agent/skills/total-recall/plugins/git/README.md +25 -1
- package/scaffold/.agent/skills/total-recall/plugins/git/cli.mjs +5 -1
- package/scaffold/.agent/skills/total-recall/plugins/git/package-lock.json +6 -6
- package/scaffold/.agent/skills/total-recall/plugins/git/package.json +2 -1
- package/scaffold/.agent/skills/total-recall/plugins/git/plugin.json +17 -27
- package/scaffold/.agent/skills/total-recall/plugins/git/src/ops/commit-memory.mjs +30 -6
- package/scaffold/.agent/skills/total-recall/plugins/git/src/ops/fleet.mjs +24 -6
- package/scaffold/.agent/skills/total-recall/plugins/git/src/ops/secret-firewall.mjs +33 -7
- package/scaffold/.agent/skills/total-recall/plugins/git/src/ops/undo.mjs +29 -5
- package/scaffold/.agent/skills/total-recall/plugins/git/src/ops/unmerged.mjs +182 -0
- package/scaffold/.agent/skills/total-recall/plugins/git/ui/chunks/change-comparison.md +27 -0
- package/scaffold/.agent/skills/total-recall/plugins/git/ui/chunks/commit-identity.md +22 -0
- package/scaffold/.agent/skills/total-recall/plugins/git/ui/chunks/create-worktree.md +25 -0
- package/scaffold/.agent/skills/total-recall/plugins/git/ui/chunks/registered-worktrees.md +22 -0
- package/scaffold/.agent/skills/total-recall/plugins/git/ui/chunks/remove-worktree.md +23 -0
- package/scaffold/.agent/skills/total-recall/plugins/git/ui/chunks/repository-ledger.md +25 -0
- package/scaffold/.agent/skills/total-recall/plugins/git/ui/chunks/unmerged-work.md +22 -0
- package/scaffold/.agent/skills/total-recall/plugins/git/ui/chunks/upstream-divergence.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/git/ui/chunks/worktree-conflict-triage.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/git/ui/chunks/worktree-terminal.md +22 -0
- package/scaffold/.agent/skills/total-recall/plugins/git/ui/home.js +273 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/DESIGN.md +35 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/README.md +4 -5
- package/scaffold/.agent/skills/total-recall/plugins/mesh/cli.mjs +9 -3
- package/scaffold/.agent/skills/total-recall/plugins/mesh/package-lock.json +6 -6
- package/scaffold/.agent/skills/total-recall/plugins/mesh/package.json +2 -1
- package/scaffold/.agent/skills/total-recall/plugins/mesh/plugin.json +37 -39
- package/scaffold/.agent/skills/total-recall/plugins/mesh/src/cli/mesh.mjs +5 -3
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/active-device-dispatch.md +22 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/control-probe.md +25 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/control-server.md +22 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/credential-readiness.md +23 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/elected-leader.md +22 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/enrollment-key.md +22 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/file-receipt.md +25 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/fleet-execution.md +23 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/fleet-presence.md +23 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/interactive-ssh.md +22 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/local-enrollment.md +23 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/mesh-policy.md +23 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/network-atlas.md +25 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/node-roster.md +26 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/node-selection-proof.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/owner-observations.md +23 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/peer-path.md +23 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/pinned-leader.md +24 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/reachability-evidence-ladder.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/recorded-login.md +23 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/remote-execution.md +22 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/chunks/secret-grants.md +26 -0
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/{card.js → home.js} +93 -22
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/DESIGN.md +86 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/README.md +19 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/cli.mjs +5 -1
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/package-lock.json +6 -6
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/package.json +2 -1
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/plugin.json +43 -22
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/src/chat.mjs +80 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/chunks/adapter-docs-freshness.md +16 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/chunks/chat-handoff.md +26 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/chunks/fleet-maintenance.md +21 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/chunks/harness-inventory.md +21 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/chunks/included-access.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/chunks/included-usage-verification.md +15 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/chunks/independent-review.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/chunks/managed-execution.md +20 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/chunks/official-documentation.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/chunks/quota-recovery.md +21 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/chunks/review-routing-decision.md +16 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/chunks/route-work.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/chunks/routing-evidence.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/chunks/run-ledger.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/home.js +198 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/DESIGN.md +75 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/README.md +2 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/cli.mjs +17 -14
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/package-lock.json +6 -6
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/package.json +2 -1
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/plugin.json +10 -44
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/src/generate.mjs +5 -4
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/src/graph.mjs +3 -4
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/src/ingest.mjs +23 -18
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/src/mesh-vaults.mjs +8 -3
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/src/refresh.mjs +6 -3
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/src/search.mjs +3 -5
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/src/token.mjs +21 -47
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/src/upstream-watcher.mjs +17 -6
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/auto-refresh.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/bootstrap-pages.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/generate-wiki.md +21 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/generator-settings.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/host-probe.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/ingest-preview.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/link-hygiene.md +21 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/link-topology.md +19 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/passage-search.md +19 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/propagation-plan.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/provider-credentials.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/refresh-report.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/task-evidence.md +22 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/upstream-record.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/watch-upstream.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/chunks/wiki-atlas.md +19 -0
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/panel.js +261 -513
- package/scaffold/.agent/skills/total-recall/plugins/security/DESIGN.md +84 -0
- package/scaffold/.agent/skills/total-recall/plugins/security/README.md +4 -2
- package/scaffold/.agent/skills/total-recall/plugins/security/cli.mjs +7 -19
- package/scaffold/.agent/skills/total-recall/plugins/security/package-lock.json +6 -6
- package/scaffold/.agent/skills/total-recall/plugins/security/package.json +2 -3
- package/scaffold/.agent/skills/total-recall/plugins/security/plugin.json +19 -52
- package/scaffold/.agent/skills/total-recall/plugins/security/ui/chunks/device-evidence.md +21 -0
- package/scaffold/.agent/skills/total-recall/plugins/security/ui/chunks/evidence-desk.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/security/ui/chunks/guided-device-review.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/security/ui/chunks/host-and-network.md +21 -0
- package/scaffold/.agent/skills/total-recall/plugins/security/ui/chunks/https-headers.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/security/ui/chunks/mesh-coverage.md +18 -0
- package/scaffold/.agent/skills/total-recall/plugins/security/ui/chunks/private-security-tools.md +16 -0
- package/scaffold/.agent/skills/total-recall/plugins/security/ui/chunks/single-origin-header-check.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/security/ui/chunks/source-review.md +21 -0
- package/scaffold/.agent/skills/total-recall/plugins/security/ui/chunks/ssh-permission-plan.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/security/ui/home.js +283 -0
- package/scaffold/.agent/skills/total-recall/plugins/ssss/DESIGN.md +93 -0
- package/scaffold/.agent/skills/total-recall/plugins/ssss/package-lock.json +2 -2
- package/scaffold/.agent/skills/total-recall/plugins/ssss/package.json +2 -1
- package/scaffold/.agent/skills/total-recall/plugins/ssss/plugin.json +5 -3
- package/scaffold/.agent/skills/total-recall/plugins/ssss/ui/chunks/conformance.md +26 -0
- package/scaffold/.agent/skills/total-recall/plugins/ssss/ui/chunks/registry.md +37 -0
- package/scaffold/.agent/skills/total-recall/plugins/ssss/ui/chunks/repair.md +42 -0
- package/scaffold/.agent/skills/total-recall/plugins/ssss/ui/chunks/scaffold.md +33 -0
- package/scaffold/.agent/skills/total-recall/plugins/ssss/ui/chunks/status.md +43 -0
- package/scaffold/.agent/skills/total-recall/plugins/ssss/ui/chunks/validate.md +34 -0
- package/scaffold/.agent/skills/total-recall/plugins/ssss/ui/chunks/validation-diagnostics.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/ssss/ui/chunks/workspace-registry-preflight.md +17 -0
- package/scaffold/.agent/skills/total-recall/plugins/ssss/ui/home.js +348 -0
- package/scaffold/.agent/skills/total-recall/references/operations.md +2 -0
- package/src/cli/api.mjs +3 -3
- package/src/cli/brief.mjs +3 -0
- package/src/cli/config.mjs +16 -0
- package/src/cli/connect.mjs +2 -7
- package/src/cli/plugin/chunks.mjs +145 -0
- package/src/cli/plugin/create.mjs +24 -52
- package/src/cli/plugin/index.mjs +20 -9
- package/src/cli/setup.mjs +2 -9
- package/src/cli/start.mjs +1 -0
- package/src/cli/startup.mjs +18 -0
- package/src/core/app-deploy/design-tokens.mjs +14 -9
- package/src/core/app-deploy/ui-elements.mjs +1 -1
- package/src/core/brain-registry.mjs +5 -0
- package/src/core/brain-updates.mjs +5 -1
- package/src/core/daemon-control.mjs +5 -1
- package/src/core/dashboard-bundle.mjs +261 -0
- package/src/core/default-plugin-refresh.mjs +39 -0
- package/src/core/ensure-dependencies.mjs +19 -15
- package/src/core/memory-brain.mjs +30 -8
- package/src/core/plugin-activation.mjs +63 -20
- package/src/core/plugin-contracts/{card.mjs → manifest.mjs} +23 -57
- package/src/core/plugin-contracts/startup-check.mjs +49 -0
- package/src/core/plugin-contracts/ui.mjs +9 -3
- package/src/core/plugin-distribution.mjs +6 -6
- package/src/core/plugin-lifecycle.mjs +58 -0
- package/src/core/plugin-loader.mjs +9 -5
- package/src/core/plugin-runner.mjs +21 -10
- package/src/core/plugin-startup-checks.mjs +44 -0
- package/src/core/plugin-state.mjs +19 -5
- package/src/core/plugin-store.mjs +30 -11
- package/src/core/project-id.mjs +15 -5
- package/src/core/required-plugins.mjs +31 -6
- package/src/core/schema.mjs +2 -0
- package/src/core/ssss-operation-service.mjs +1 -0
- package/src/core/startup-health.mjs +28 -3
- package/src/core/testing/plugin-fixture.mjs +22 -21
- package/src/core/throttled-fetch.mjs +25 -18
- package/src/core/ui-chunk-choice.mjs +77 -0
- package/src/core/ui-chunk.registry.json +23 -0
- package/src/core/ui-chunks.mjs +434 -0
- package/src/core/vault-cache.mjs +58 -59
- package/src/core/workspace-compositions.mjs +151 -0
- package/src/core/workspace-drawers.mjs +79 -0
- package/src/server/api.mjs +4 -27
- package/src/server/index.mjs +28 -21
- package/src/server/memory-events.mjs +31 -0
- package/src/server/plugin-brain-targets.mjs +89 -0
- package/src/server/rest.mjs +2 -0
- package/src/server/route-inventory.mjs +3 -2
- package/src/server/route-manifest.json +52 -4
- package/src/server/routes/_shared.mjs +7 -14
- package/src/server/routes/brains.mjs +29 -44
- package/src/server/routes/dashboard.mjs +26 -0
- package/src/server/routes/plugins.mjs +154 -45
- package/src/server/routes/ui-chunks.mjs +192 -0
- package/frontend/dist/assets/index-DACh1dhx.js +0 -5613
- package/frontend/dist/assets/index-DtwsDyFM.css +0 -1
- package/frontend/src/components/plugins/card/CardEngine.tsx +0 -108
- package/frontend/src/components/plugins/card/CardScenes.tsx +0 -103
- package/frontend/src/components/plugins/card/ExecutionPicker.tsx +0 -64
- package/frontend/src/components/plugins/card/args.ts +0 -28
- package/frontend/src/components/plugins/card/card.css +0 -32
- package/frontend/src/components/plugins/card/cli-line.ts +0 -13
- package/frontend/src/components/plugins/card/contract.ts +0 -91
- package/frontend/src/components/plugins/card/format.ts +0 -49
- package/frontend/src/components/plugins/card/runner-context.ts +0 -11
- package/frontend/src/components/plugins/card/runner.tsx +0 -43
- package/frontend/src/components/plugins/card/theme.ts +0 -35
- package/frontend/src/components/plugins/card/use-source.ts +0 -22
- package/frontend/src/components/plugins/card/widgets.tsx +0 -94
- package/frontend/src/components/plugins/workspace/WorkspaceHost.tsx +0 -23
- package/frontend/src/pages/PluginsPage.tsx +0 -1719
- package/scaffold/.agent/skills/plugin/evals/cases/04-card-collects-credential.mjs +0 -47
- package/scaffold/.agent/skills/plugin/prompts/06-card.md +0 -46
- package/scaffold/.agent/skills/plugin/references/card.md +0 -90
- package/scaffold/.agent/skills/plugin/subagents/card-designer.md +0 -60
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/DESIGN.md +0 -67
- package/scaffold/.agent/skills/total-recall/plugins/auth/ui/card.js +0 -1179
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/ui/DESIGN.md +0 -32
- package/scaffold/.agent/skills/total-recall/plugins/code-quality/ui/card.js +0 -588
- package/scaffold/.agent/skills/total-recall/plugins/composable-cli/ui/card.js +0 -575
- package/scaffold/.agent/skills/total-recall/plugins/embeddings/ui/DESIGN.md +0 -32
- package/scaffold/.agent/skills/total-recall/plugins/embeddings/ui/card.js +0 -482
- package/scaffold/.agent/skills/total-recall/plugins/git/ui/DESIGN.md +0 -100
- package/scaffold/.agent/skills/total-recall/plugins/git/ui/card.js +0 -637
- package/scaffold/.agent/skills/total-recall/plugins/mesh/ui/DESIGN.md +0 -217
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/DESIGN.md +0 -32
- package/scaffold/.agent/skills/total-recall/plugins/meta-harness/ui/card.js +0 -1276
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/DESIGN.md +0 -45
- package/scaffold/.agent/skills/total-recall/plugins/openwiki/ui/card.js +0 -1401
- package/scaffold/.agent/skills/total-recall/plugins/security/scripts/build-ui.mjs +0 -4
- package/scaffold/.agent/skills/total-recall/plugins/security/ui/DESIGN.md +0 -41
- package/scaffold/.agent/skills/total-recall/plugins/security/ui/card.js +0 -396
- package/scaffold/.agent/skills/total-recall/plugins/security/ui/panel.js +0 -98
- package/scaffold/.agent/skills/total-recall/plugins/ssss/ui/DESIGN.md +0 -15
- package/scaffold/.agent/skills/total-recall/plugins/ssss/ui/card.js +0 -182
|
@@ -0,0 +1,375 @@
|
|
|
1
|
+
const template = document.createElement('template');
|
|
2
|
+
template.innerHTML = `
|
|
3
|
+
<style>
|
|
4
|
+
:host { display:block; color:var(--color-text,#edf6f0); font:400 .9rem/1.5 var(--typography-body-font-family,system-ui); }
|
|
5
|
+
* { box-sizing:border-box; }
|
|
6
|
+
main { background:var(--color-background,#101e19); border:1px solid var(--color-outline,#3f6350); border-radius:var(--rounded-panel,.75rem); overflow:hidden; }
|
|
7
|
+
header, .body { padding:clamp(14px,3vw,26px); }
|
|
8
|
+
header { display:flex; flex-wrap:wrap; align-items:center; justify-content:space-between; gap:12px; }
|
|
9
|
+
h1,h2,p { margin:0; }
|
|
10
|
+
h1 { font-size:clamp(1.5rem,4vw,2.25rem); letter-spacing:-.035em; line-height:1.15; }
|
|
11
|
+
h2 { font-size:1.1rem; }
|
|
12
|
+
.eyebrow { color:var(--color-primary,#64e3a4); font:600 .72rem var(--typography-label-font-family,monospace); letter-spacing:.1em; margin-bottom:6px; }
|
|
13
|
+
.muted, th { color:var(--color-muted,#b1c9ba); }
|
|
14
|
+
header p:last-child { margin-top:6px; }
|
|
15
|
+
nav { display:flex; flex-wrap:wrap; gap:4px; padding:0 clamp(14px,3vw,26px); border-block-end:1px solid var(--color-outline,#3f6350); }
|
|
16
|
+
button, input { font:inherit; color:inherit; }
|
|
17
|
+
button { min-height:44px; cursor:pointer; padding:0 12px; background:var(--color-surface,#192d24); border:1px solid var(--color-outline,#3f6350); border-radius:var(--rounded-control,.4rem); }
|
|
18
|
+
button:disabled { opacity:.65; cursor:wait; }
|
|
19
|
+
nav button { background:transparent; border:1px solid transparent; border-radius:0; color:var(--color-muted,#b1c9ba); }
|
|
20
|
+
nav button[aria-pressed="true"] { color:var(--color-primary,#64e3a4); border-block-end:2px solid currentColor; font-weight:700; }
|
|
21
|
+
button:focus-visible, input:focus-visible { outline:2px solid var(--color-primary,#64e3a4); outline-offset:2px; }
|
|
22
|
+
.tools { display:flex; align-items:center; justify-content:space-between; gap:12px; flex-wrap:wrap; margin-bottom:12px; }
|
|
23
|
+
label { display:flex; flex-wrap:wrap; align-items:center; gap:8px; }
|
|
24
|
+
input { background:var(--color-surface,#192d24); border:1px solid var(--color-outline,#3f6350); border-radius:var(--rounded-control,.4rem); min-height:44px; padding:6px 10px; max-width:100%; }
|
|
25
|
+
.table { overflow:auto; max-height:430px; }
|
|
26
|
+
table { width:100%; border-collapse:collapse; text-align:start; }
|
|
27
|
+
th, td { padding:9px 10px; text-align:start; border-block-end:1px solid var(--color-outline,#3f6350); vertical-align:top; }
|
|
28
|
+
th { position:sticky; top:0; background:var(--color-surface,#192d24); font-size:.75rem; }
|
|
29
|
+
td { overflow-wrap:anywhere; }
|
|
30
|
+
td.actions { white-space:nowrap; }
|
|
31
|
+
td.actions button + button { margin-inline-start:6px; }
|
|
32
|
+
select { font:inherit; min-height:44px; color:inherit; background:var(--color-surface,#192d24); border:1px solid var(--color-outline,#3f6350); border-radius:var(--rounded-control,.4rem); padding:6px 10px; }
|
|
33
|
+
dialog { color:inherit; background:var(--color-background,#101e19); border:1px solid var(--color-outline,#3f6350); border-radius:var(--rounded-panel,.75rem); padding:20px; width:min(480px,calc(100% - 26px)); max-height:calc(100% - 26px); }
|
|
34
|
+
dialog::backdrop { background:#08110dcc; }
|
|
35
|
+
dialog label { display:grid; margin:10px 0; }
|
|
36
|
+
dialog .tools { margin:12px 0 0; }
|
|
37
|
+
.state-ready { color:var(--color-primary,#64e3a4); }
|
|
38
|
+
.state-attention { color:var(--color-warning,#f4d18c); }
|
|
39
|
+
[role="alert"] { color:var(--color-danger,#ffbbb1); }
|
|
40
|
+
dl { margin:0 0 16px; }
|
|
41
|
+
dl div { display:flex; justify-content:space-between; flex-wrap:wrap; padding:8px 0; border-block-end:1px solid var(--color-outline,#3f6350); }
|
|
42
|
+
dd { margin:0; }
|
|
43
|
+
#audit-result { margin:8px 0; }
|
|
44
|
+
[hidden] { display:none!important; }
|
|
45
|
+
</style>
|
|
46
|
+
<main aria-labelledby="auth-title">
|
|
47
|
+
<header>
|
|
48
|
+
<div><p class="eyebrow">ACCESS CONTROL</p><h1 id="auth-title">Auth & Secrets</h1>
|
|
49
|
+
<p class="muted">Credentials and access across this host’s brains and machines.</p></div>
|
|
50
|
+
<button type="button" id="refresh">Refresh</button>
|
|
51
|
+
</header>
|
|
52
|
+
<nav aria-label="Auth views">
|
|
53
|
+
<button type="button" data-view="secrets" aria-pressed="true">Secrets</button>
|
|
54
|
+
<button type="button" data-view="brains" aria-pressed="false">Brains</button>
|
|
55
|
+
<button type="button" data-view="machines" aria-pressed="false">Machines</button>
|
|
56
|
+
<button type="button" data-view="sign-in" aria-pressed="false">Sign-in & audit</button>
|
|
57
|
+
</nav>
|
|
58
|
+
<section class="body" id="inventory" aria-label="Inventory">
|
|
59
|
+
<div class="tools">
|
|
60
|
+
<p id="summary" role="status"></p>
|
|
61
|
+
<label id="repo-filter-label" hidden>Repository<select id="repo-filter"></select></label>
|
|
62
|
+
<label id="search-label">Filter inventory<input type="search" id="search" autocomplete="off"></label>
|
|
63
|
+
</div>
|
|
64
|
+
<p id="problem" role="alert" hidden></p>
|
|
65
|
+
<p id="receipt" role="status" hidden></p>
|
|
66
|
+
<div class="table" id="table" role="region" aria-label="Inventory results" tabindex="0" hidden></div>
|
|
67
|
+
</section>
|
|
68
|
+
<section class="body" id="sign-in" aria-label="Sign-in and audit" hidden>
|
|
69
|
+
<dl aria-live="polite">
|
|
70
|
+
<div><dt>Registered passkeys</dt><dd id="passkeys">Checking…</dd></div>
|
|
71
|
+
<div><dt>Google sign-in configuration</dt><dd id="google">Checking…</dd></div>
|
|
72
|
+
<div><dt>Dashboard session signing</dt><dd id="session">Checking…</dd></div>
|
|
73
|
+
</dl>
|
|
74
|
+
<h2>Security baseline</h2>
|
|
75
|
+
<p id="audit-result" role="status">Check the current host configuration.</p>
|
|
76
|
+
<button type="button" id="audit">Run baseline audit</button>
|
|
77
|
+
</section>
|
|
78
|
+
<dialog id="credential-dialog" aria-labelledby="credential-heading">
|
|
79
|
+
<h2 id="credential-heading"></h2>
|
|
80
|
+
<p id="credential-key"></p>
|
|
81
|
+
<div id="credential-fields">
|
|
82
|
+
<label>Label<input id="credential-label" maxlength="120" autocomplete="off"></label>
|
|
83
|
+
<label>Repository binding<input id="credential-repo" maxlength="256" list="registered-repositories" autocomplete="off"></label>
|
|
84
|
+
<datalist id="registered-repositories"></datalist>
|
|
85
|
+
<button type="button" id="credential-clear-repo">Clear binding</button>
|
|
86
|
+
<p class="muted" id="binding-status"></p>
|
|
87
|
+
<label>Replacement value<input type="password" id="credential-value" maxlength="16384" autocomplete="new-password"></label>
|
|
88
|
+
</div>
|
|
89
|
+
<div id="delete-fields" hidden>
|
|
90
|
+
<p>Remove this credential from this host’s encrypted store. Enter its name to confirm.</p>
|
|
91
|
+
<label>Credential name<input id="credential-confirm" maxlength="256" autocomplete="off"></label>
|
|
92
|
+
</div>
|
|
93
|
+
<p id="credential-error" role="alert" hidden></p>
|
|
94
|
+
<div class="tools">
|
|
95
|
+
<button type="button" id="credential-close">Cancel</button>
|
|
96
|
+
<button type="button" id="credential-replace">Replace value</button>
|
|
97
|
+
<button type="button" id="credential-save">Save details</button>
|
|
98
|
+
</div>
|
|
99
|
+
</dialog>
|
|
100
|
+
</main>
|
|
101
|
+
`;
|
|
102
|
+
|
|
103
|
+
const count = value => Number.isSafeInteger(value) && value >= 0;
|
|
104
|
+
const words = values => Array.isArray(values) && values.length ? values.join(', ') : 'Unbound';
|
|
105
|
+
const date = value => typeof value === 'string' && Number.isFinite(Date.parse(value))
|
|
106
|
+
? new Intl.DateTimeFormat(undefined, { dateStyle: 'medium' }).format(new Date(value)) : 'Unscheduled';
|
|
107
|
+
const state = (value, positive, negative) => value === true ? positive : value === false ? negative : 'Unreported';
|
|
108
|
+
|
|
109
|
+
const views = {
|
|
110
|
+
secrets: {
|
|
111
|
+
name: 'credentials', headers: ['Credential', 'Provider', 'Bound repositories', 'Storage', 'Rotation'],
|
|
112
|
+
row: item => [item.label ? `${item.key} · ${item.label}` : item.key, item.provider_name || 'Unassigned', words(item.repos),
|
|
113
|
+
state(item.set, 'Stored', 'Empty'), item.rotation_overdue ? 'Overdue' : date(item.next_rotate_due)],
|
|
114
|
+
},
|
|
115
|
+
brains: {
|
|
116
|
+
name: 'brains', headers: ['Brain', 'Layer', 'Memory nodes', 'State'],
|
|
117
|
+
row: item => [item.name, item.layer, count(item.node_count) ? String(item.node_count) : 'Unreported',
|
|
118
|
+
state(item.exists, 'Present', 'Unavailable')],
|
|
119
|
+
},
|
|
120
|
+
machines: {
|
|
121
|
+
name: 'machines', headers: ['Machine', 'OS', 'Role', 'Mesh state'],
|
|
122
|
+
row: item => [item.self ? item.hostname + ' (this host)' : item.hostname, item.os || 'Unreported',
|
|
123
|
+
item.role || 'Unassigned', item.vault_only ? 'Registered' : state(item.online, 'Online', 'Offline')],
|
|
124
|
+
},
|
|
125
|
+
};
|
|
126
|
+
|
|
127
|
+
class AuthHome extends HTMLElement {
|
|
128
|
+
constructor() {
|
|
129
|
+
super();
|
|
130
|
+
this.activeView = 'secrets';
|
|
131
|
+
this.inventory = {};
|
|
132
|
+
this.attachShadow({ mode: 'open' }).append(template.content.cloneNode(true));
|
|
133
|
+
this.field('refresh').addEventListener('click', () => void this.load());
|
|
134
|
+
this.field('audit').addEventListener('click', () => void this.audit());
|
|
135
|
+
this.field('search').addEventListener('input', () => this.renderInventory());
|
|
136
|
+
this.field('repo-filter').addEventListener('change', () => this.renderInventory());
|
|
137
|
+
this.field('credential-close').addEventListener('click', () => this.field('credential-dialog').close());
|
|
138
|
+
this.field('credential-save').addEventListener('click', () => void this.changeCredential(this.credentialAction));
|
|
139
|
+
this.field('credential-replace').addEventListener('click', () => void this.changeCredential('replace'));
|
|
140
|
+
this.field('credential-repo').addEventListener('input', () => { this.bindingChanged = true; });
|
|
141
|
+
this.field('credential-clear-repo').addEventListener('click', () => {
|
|
142
|
+
this.bindingChanged = true;
|
|
143
|
+
this.field('credential-repo').value = '';
|
|
144
|
+
this.field('binding-status').textContent = 'The binding will be cleared when you save.';
|
|
145
|
+
});
|
|
146
|
+
this.field('credential-dialog').addEventListener('cancel', event => {
|
|
147
|
+
if (this.credentialBusy) event.preventDefault();
|
|
148
|
+
});
|
|
149
|
+
this.field('credential-dialog').addEventListener('close', () => {
|
|
150
|
+
this.field('credential-value').value = '';
|
|
151
|
+
this.field('credential-confirm').value = '';
|
|
152
|
+
});
|
|
153
|
+
for (const button of this.shadowRoot.querySelectorAll('[data-view]')) {
|
|
154
|
+
button.addEventListener('click', () => {
|
|
155
|
+
this.activeView = button.dataset.view;
|
|
156
|
+
this.field('search').value = '';
|
|
157
|
+
for (const item of this.shadowRoot.querySelectorAll('[data-view]')) {
|
|
158
|
+
item.setAttribute('aria-pressed', String(item === button));
|
|
159
|
+
}
|
|
160
|
+
this.renderInventory();
|
|
161
|
+
});
|
|
162
|
+
}
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
field(id) { return this.shadowRoot.getElementById(id); }
|
|
166
|
+
|
|
167
|
+
repoAliases() {
|
|
168
|
+
const groups = new Map();
|
|
169
|
+
for (const brain of this.inventory.brains?.rows || []) {
|
|
170
|
+
if (brain.layer !== 'project' || typeof brain.name !== 'string') continue;
|
|
171
|
+
const normalized = brain.name.toLowerCase().replaceAll('_', '-');
|
|
172
|
+
const labels = groups.get(normalized) || new Set();
|
|
173
|
+
labels.add(brain.name);
|
|
174
|
+
groups.set(normalized, labels);
|
|
175
|
+
}
|
|
176
|
+
return new Map([...groups].filter(([, labels]) => labels.size === 1)
|
|
177
|
+
.map(([key, labels]) => [key, [...labels][0]]));
|
|
178
|
+
}
|
|
179
|
+
|
|
180
|
+
renderInventory() {
|
|
181
|
+
const signing = this.activeView === 'sign-in';
|
|
182
|
+
this.field('sign-in').hidden = !signing;
|
|
183
|
+
this.field('inventory').hidden = signing;
|
|
184
|
+
if (signing) return;
|
|
185
|
+
|
|
186
|
+
const view = views[this.activeView];
|
|
187
|
+
const result = this.inventory[this.activeView];
|
|
188
|
+
const problem = this.field('problem');
|
|
189
|
+
const tableRegion = this.field('table');
|
|
190
|
+
const summary = this.field('summary');
|
|
191
|
+
const search = this.field('search');
|
|
192
|
+
const repoFilter = this.field('repo-filter');
|
|
193
|
+
const credentials = this.activeView === 'secrets';
|
|
194
|
+
problem.hidden = !result?.error;
|
|
195
|
+
problem.textContent = result?.error || '';
|
|
196
|
+
tableRegion.hidden = true;
|
|
197
|
+
tableRegion.replaceChildren();
|
|
198
|
+
this.field('search-label').hidden = !result?.rows?.length;
|
|
199
|
+
this.field('repo-filter-label').hidden = !credentials || !result?.rows?.length;
|
|
200
|
+
if (!result) { summary.textContent = `Loading ${view.name}…`; return; }
|
|
201
|
+
if (result.error) { summary.textContent = ''; return; }
|
|
202
|
+
|
|
203
|
+
const aliases = credentials ? this.repoAliases() : new Map();
|
|
204
|
+
const repoLabels = item => [...new Set((Array.isArray(item.repos) ? item.repos : []).filter(repo => typeof repo === 'string').map(repo =>
|
|
205
|
+
aliases.get(repo.toLowerCase().replaceAll('_', '-')) || repo))];
|
|
206
|
+
const selectedRepo = repoFilter.value;
|
|
207
|
+
if (credentials) {
|
|
208
|
+
const repos = [...new Set(result.rows.flatMap(repoLabels))].sort((left, right) => left.localeCompare(right));
|
|
209
|
+
repoFilter.replaceChildren(new Option('All repositories', ''),
|
|
210
|
+
...repos.map(repo => new Option(repo, repo)));
|
|
211
|
+
if (repos.includes(selectedRepo)) repoFilter.value = selectedRepo;
|
|
212
|
+
}
|
|
213
|
+
const query = search.value.trim().toLocaleLowerCase();
|
|
214
|
+
const rows = result.rows.flatMap(item => {
|
|
215
|
+
const repos = credentials ? repoLabels(item) : [];
|
|
216
|
+
if (credentials && repoFilter.value && !repos.includes(repoFilter.value)) return [];
|
|
217
|
+
const values = view.row(credentials ? { ...item, repos } : item);
|
|
218
|
+
const searchText = values.concat(credentials ? item.repos || [] : []).join(' ').toLocaleLowerCase();
|
|
219
|
+
return searchText.includes(query) ? [{ item, values }] : [];
|
|
220
|
+
});
|
|
221
|
+
summary.textContent = rows.length === result.rows.length
|
|
222
|
+
? `${result.rows.length} ${view.name}` : `${rows.length} of ${result.rows.length} ${view.name}`;
|
|
223
|
+
if (!rows.length) return;
|
|
224
|
+
const table = document.createElement('table');
|
|
225
|
+
table.setAttribute('aria-label', view.name);
|
|
226
|
+
const heading = table.createTHead().insertRow();
|
|
227
|
+
const canEdit = credentials && typeof this.host?.changeCredential === 'function';
|
|
228
|
+
for (const title of canEdit ? [...view.headers, 'Manage'] : view.headers) {
|
|
229
|
+
const cell = document.createElement('th');
|
|
230
|
+
cell.scope = 'col';
|
|
231
|
+
cell.textContent = title;
|
|
232
|
+
heading.append(cell);
|
|
233
|
+
}
|
|
234
|
+
const body = table.createTBody();
|
|
235
|
+
for (const { item, values } of rows) {
|
|
236
|
+
const entry = body.insertRow();
|
|
237
|
+
for (const value of values) {
|
|
238
|
+
const cell = entry.insertCell();
|
|
239
|
+
cell.textContent = value ?? 'Unreported';
|
|
240
|
+
if (['Stored', 'Online', 'Present'].includes(value)) cell.className = 'state-ready';
|
|
241
|
+
if (['Overdue', 'Offline', 'Empty'].includes(value)) cell.className = 'state-attention';
|
|
242
|
+
}
|
|
243
|
+
if (canEdit) {
|
|
244
|
+
const actions = entry.insertCell();
|
|
245
|
+
actions.className = 'actions';
|
|
246
|
+
for (const [action, label] of [['edit', 'Edit'], ['delete', 'Delete']]) {
|
|
247
|
+
const button = document.createElement('button');
|
|
248
|
+
button.type = 'button';
|
|
249
|
+
button.textContent = label;
|
|
250
|
+
button.setAttribute('aria-label', `${label} ${item.key}`);
|
|
251
|
+
button.addEventListener('click', () => this.openCredential(item, action));
|
|
252
|
+
actions.append(button);
|
|
253
|
+
}
|
|
254
|
+
}
|
|
255
|
+
}
|
|
256
|
+
tableRegion.append(table);
|
|
257
|
+
tableRegion.hidden = false;
|
|
258
|
+
}
|
|
259
|
+
|
|
260
|
+
openCredential(item, action) {
|
|
261
|
+
const deleting = action === 'delete';
|
|
262
|
+
this.selectedCredential = item;
|
|
263
|
+
this.credentialAction = action;
|
|
264
|
+
this.bindingChanged = false;
|
|
265
|
+
this.field('credential-heading').textContent = deleting ? 'Delete stored credential' : 'Edit credential';
|
|
266
|
+
this.field('credential-key').textContent = item.key;
|
|
267
|
+
this.field('credential-fields').hidden = deleting;
|
|
268
|
+
this.field('delete-fields').hidden = !deleting;
|
|
269
|
+
this.field('credential-replace').hidden = deleting;
|
|
270
|
+
this.field('credential-save').textContent = deleting ? 'Delete credential' : 'Save details';
|
|
271
|
+
this.field('credential-label').value = item.label || '';
|
|
272
|
+
this.field('credential-repo').value = (item.repos || []).length <= 1 ? item.repos?.[0] || '' : '';
|
|
273
|
+
this.field('registered-repositories').replaceChildren(
|
|
274
|
+
...[...this.repoAliases().values()].sort().map(repo => new Option(repo, repo)),
|
|
275
|
+
);
|
|
276
|
+
this.field('credential-error').hidden = true;
|
|
277
|
+
this.field('binding-status').textContent = item.repos?.length > 1
|
|
278
|
+
? `Current bindings: ${item.repos.join(', ')}. Select one repository to replace them.`
|
|
279
|
+
: '';
|
|
280
|
+
this.field('credential-dialog').showModal();
|
|
281
|
+
}
|
|
282
|
+
|
|
283
|
+
async changeCredential(action) {
|
|
284
|
+
if (this.credentialBusy || !this.selectedCredential) return;
|
|
285
|
+
const { key } = this.selectedCredential;
|
|
286
|
+
const error = this.field('credential-error');
|
|
287
|
+
const data = { action, key };
|
|
288
|
+
if (action === 'edit') {
|
|
289
|
+
data.label = this.field('credential-label').value;
|
|
290
|
+
if (this.bindingChanged) data.repo = this.field('credential-repo').value;
|
|
291
|
+
} else if (action === 'replace') {
|
|
292
|
+
data.value = this.field('credential-value').value;
|
|
293
|
+
this.field('credential-value').value = '';
|
|
294
|
+
} else {
|
|
295
|
+
data.confirm = this.field('credential-confirm').value;
|
|
296
|
+
}
|
|
297
|
+
this.credentialBusy = true;
|
|
298
|
+
const controls = ['credential-close', 'credential-save', 'credential-replace'];
|
|
299
|
+
for (const id of controls) this.field(id).disabled = true;
|
|
300
|
+
error.hidden = true;
|
|
301
|
+
try {
|
|
302
|
+
const result = await this.host.changeCredential(data);
|
|
303
|
+
if (result?.ok !== true) throw new Error('Auth did not confirm the change.');
|
|
304
|
+
this.field('credential-dialog').close();
|
|
305
|
+
const receipt = this.field('receipt');
|
|
306
|
+
receipt.textContent = action === 'delete' ? `Deleted ${key} from this host’s store.`
|
|
307
|
+
: action === 'replace' ? `Replaced the stored value for ${key}.` : `Saved details for ${key}.`;
|
|
308
|
+
receipt.hidden = false;
|
|
309
|
+
await this.load();
|
|
310
|
+
} catch (failure) {
|
|
311
|
+
error.textContent = failure.message;
|
|
312
|
+
error.hidden = false;
|
|
313
|
+
} finally {
|
|
314
|
+
this.credentialBusy = false;
|
|
315
|
+
for (const id of controls) this.field(id).disabled = false;
|
|
316
|
+
}
|
|
317
|
+
}
|
|
318
|
+
|
|
319
|
+
async load() {
|
|
320
|
+
const button = this.field('refresh');
|
|
321
|
+
if (button.disabled) return;
|
|
322
|
+
button.disabled = true;
|
|
323
|
+
this.inventory = {};
|
|
324
|
+
this.renderInventory();
|
|
325
|
+
await Promise.all([
|
|
326
|
+
...Object.keys(views).map(async resource => {
|
|
327
|
+
try {
|
|
328
|
+
const rows = await this.host.readInventory(resource);
|
|
329
|
+
if (!Array.isArray(rows)) throw new Error('Incomplete inventory response');
|
|
330
|
+
this.inventory[resource] = { rows };
|
|
331
|
+
} catch (error) {
|
|
332
|
+
this.inventory[resource] = { error: `Could not load ${views[resource].name}. ${error.message}` };
|
|
333
|
+
}
|
|
334
|
+
this.renderInventory();
|
|
335
|
+
}),
|
|
336
|
+
this.loadSignIn(),
|
|
337
|
+
]);
|
|
338
|
+
button.disabled = false;
|
|
339
|
+
}
|
|
340
|
+
|
|
341
|
+
async loadSignIn() {
|
|
342
|
+
for (const id of ['passkeys', 'google', 'session']) this.field(id).textContent = 'Checking…';
|
|
343
|
+
const [status, session] = await Promise.allSettled([
|
|
344
|
+
this.host?.run('status'), this.host?.run('session'),
|
|
345
|
+
]);
|
|
346
|
+
const providers = status.status === 'fulfilled' ? status.value : null;
|
|
347
|
+
const registered = providers?.passkey?.registered_count;
|
|
348
|
+
this.field('passkeys').textContent = count(registered) ? String(registered) : 'Unavailable';
|
|
349
|
+
this.field('google').textContent = state(providers?.google_oauth2?.configured, 'Configured', 'Needs setup');
|
|
350
|
+
this.field('session').textContent = state(session.status === 'fulfilled' && session.value
|
|
351
|
+
? session.value.session_secret_configured : null, 'Configured', 'Needs setup');
|
|
352
|
+
}
|
|
353
|
+
|
|
354
|
+
async audit() {
|
|
355
|
+
const button = this.field('audit');
|
|
356
|
+
const result = this.field('audit-result');
|
|
357
|
+
if (button.disabled) return;
|
|
358
|
+
button.disabled = true;
|
|
359
|
+
result.textContent = 'Checking this host…';
|
|
360
|
+
try {
|
|
361
|
+
let report;
|
|
362
|
+
try { report = await this.host.run('audit'); }
|
|
363
|
+
catch (error) { report = JSON.parse(error.message); }
|
|
364
|
+
if (typeof report?.passed !== 'boolean' || !count(report.findings_count)) throw new Error('Invalid audit response');
|
|
365
|
+
const findings = `${report.findings_count} ${report.findings_count === 1 ? 'finding' : 'findings'}`;
|
|
366
|
+
result.textContent = report.passed ? `Baseline passed with ${findings}.` : `Review required. ${findings}.`;
|
|
367
|
+
result.className = report.passed && !report.findings_count ? 'state-ready' : 'state-attention';
|
|
368
|
+
} catch {
|
|
369
|
+
result.textContent = 'Baseline audit unavailable. Retry or run auth audit in the terminal.';
|
|
370
|
+
result.className = 'state-attention';
|
|
371
|
+
} finally { button.disabled = false; }
|
|
372
|
+
}
|
|
373
|
+
}
|
|
374
|
+
|
|
375
|
+
if (!customElements.get('tr-auth-home')) customElements.define('tr-auth-home', AuthHome);
|
|
@@ -1,23 +1,34 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
1
|
+
---
|
|
2
|
+
version: alpha
|
|
3
|
+
name: Automation Control Ledger
|
|
4
|
+
description: A dark operations ledger that keeps scheduling, source coverage and observed runs visually separate.
|
|
5
|
+
colors:
|
|
6
|
+
primary: "#f2bd63"
|
|
7
|
+
background: "#181713"
|
|
8
|
+
surface: "#24221c"
|
|
9
|
+
text: "#f4efe5"
|
|
10
|
+
muted: "#c5bca9"
|
|
11
|
+
border: "#726652"
|
|
12
|
+
success: "#a8d5b0"
|
|
13
|
+
error: "#ffb5a9"
|
|
14
|
+
focus: "#b8d9ff"
|
|
15
|
+
typography:
|
|
16
|
+
body: { fontFamily: "system-ui, sans-serif", fontSize: 14px, lineHeight: 1.45 }
|
|
17
|
+
label: { fontFamily: "ui-monospace, monospace", fontSize: 12px, fontWeight: 700 }
|
|
18
|
+
spacing: { sm: 8px, md: 16px, touch: 44px }
|
|
19
|
+
rounded: { md: 8px }
|
|
20
|
+
components:
|
|
21
|
+
ledger-note:
|
|
22
|
+
backgroundColor: "{colors.surface}"
|
|
23
|
+
textColor: "{colors.text}"
|
|
24
|
+
padding: "{spacing.md}"
|
|
25
|
+
rounded: "{rounded.md}"
|
|
26
|
+
ledger-label:
|
|
27
|
+
textColor: "{colors.primary}"
|
|
28
|
+
typography: "{typography.label}"
|
|
29
|
+
---
|
|
30
|
+
|
|
31
|
+
# Automations Control Ledger
|
|
21
32
|
|
|
22
33
|
## Purpose and first-principles decision
|
|
23
34
|
Greg checks which work is automated, where its source is available, and whether an observed run failed. He needs automation origins and coverage before interpreting counts. Replace the old chronometer card, fixed schedule chips and terminal output: they obscure these tasks and invent healthy state. Retain external element names and host.run because these are useful host contracts.
|
|
@@ -30,7 +41,7 @@ The first visible line states whether inventory is unchecked, loading, complete,
|
|
|
30
41
|
The selected record shows trigger, enabled state, runner availability, source, placement and origin independently. Unknown values include a reason. Failed reads clear current inventory. Unsupported sources and unavailable nodes remain visible. Counts derive only from returned records and cannot imply coverage completeness.
|
|
31
42
|
|
|
32
43
|
## Interaction and safety
|
|
33
|
-
Read through host
|
|
44
|
+
Read through the authenticated host bridge inside the sandbox. Load this node first and switch to mesh inventory through an explicit scope control. Reject failed wrappers and malformed inventory. A latest-request counter prevents stale refreshes overwriting newer results. Disconnect invalidates pending work; reconnect reuses its shadow root and selected tab.
|
|
34
45
|
|
|
35
46
|
Every control is at least 44px, with visible focus. Tabs support arrow/Home/End navigation and maintain selected-screen state. Filters have labels; loading/errors use a live region. Layout becomes one column under 600px; text wraps safely. State change motion is a short content reveal; reduced motion removes it. Copy feedback follows actual clipboard completion. Source-advertised write controls state their target and require confirmation; arbitrary commands and credential inputs are absent.
|
|
36
47
|
|
|
@@ -13,6 +13,18 @@ export const coreModule = (root, name) => import(pathToFileURL(path.join(root, '
|
|
|
13
13
|
const digest = text => crypto.createHash('sha256').update(text).digest('hex').slice(0, 20);
|
|
14
14
|
export const recordId = (node, source, key) => `${source}:${digest(`${node}\0${key}`)}`;
|
|
15
15
|
const text = (value, max = 240) => typeof value === 'string' ? value.slice(0, max) : '';
|
|
16
|
+
const credentialLine = /\b(?:authorization|bearer|password|token|credential|secret|api[-_ ]?key)\b|(?:_KEY|_TOKEN|_SECRET|_PASSWORD)\b|\b(?:sk[-_]|gh[pousr]_|github_pat_|eyJ)[a-z0-9_-]{12,}/i;
|
|
17
|
+
|
|
18
|
+
function failureReceipt(event) {
|
|
19
|
+
const output = text(event.output_tail, 2000).split('\n')
|
|
20
|
+
.map(line => credentialLine.test(line) ? '[credential diagnostic omitted]' : line)
|
|
21
|
+
.join('\n');
|
|
22
|
+
return {
|
|
23
|
+
timed_out: Boolean(event.timed_out),
|
|
24
|
+
duration_ms: Number.isFinite(event.duration_ms) ? event.duration_ms : null,
|
|
25
|
+
output_tail: output || null,
|
|
26
|
+
};
|
|
27
|
+
}
|
|
16
28
|
const canCancelPending = async (tasks, queueDir) =>
|
|
17
29
|
tasks.TASK_CANCELLATION_SUPPORTS_EXPECTED_STATUS === true
|
|
18
30
|
&& typeof tasks.supportsPendingTaskCancellation === 'function'
|
|
@@ -143,7 +155,11 @@ export async function sourceAdapters(ctx) {
|
|
|
143
155
|
const matching = payloads.filter(event => event.plugin_id === record.plugin_id && event.command === record.command)
|
|
144
156
|
.sort((a, b) => eventTime(a) - eventTime(b));
|
|
145
157
|
const last = matching.at(-1);
|
|
146
|
-
if (last)
|
|
158
|
+
if (last) {
|
|
159
|
+
record.last_run = outcome(last);
|
|
160
|
+
// The failure receipt is shown only for the record the operator asked about.
|
|
161
|
+
if (last.ok === false && ctx.receiptId === record.id) record.last_run.receipt = failureReceipt(last);
|
|
162
|
+
}
|
|
147
163
|
const handled = record.last_handled_slot && matching.filter(event => event.slot === record.last_handled_slot).at(-1);
|
|
148
164
|
if (handled) record.last_handled_outcome = outcome(handled);
|
|
149
165
|
}
|
|
@@ -17,6 +17,7 @@ Options:
|
|
|
17
17
|
--source <source> Filter records by source
|
|
18
18
|
--trigger <kind> Filter records by trigger kind
|
|
19
19
|
--state <state> Filter records by observed state
|
|
20
|
+
--receipt Include a failed plugin task receipt (show --local, terminal only)
|
|
20
21
|
--json Machine-readable output (also the default)
|
|
21
22
|
--help, -h Show this help
|
|
22
23
|
|
|
@@ -43,6 +44,7 @@ export function parseArgs(argv) {
|
|
|
43
44
|
const flag = args.shift();
|
|
44
45
|
if (flag === '--json') continue;
|
|
45
46
|
if (flag === '--local') { result.localOnly = true; continue; }
|
|
47
|
+
if (flag === '--receipt') { result.receipt = true; continue; }
|
|
46
48
|
const name = { '--node': 'node', '--source': 'source', '--trigger': 'trigger', '--state': 'state' }[flag];
|
|
47
49
|
if (!name) throw new Error(`Unknown option: ${flag}`);
|
|
48
50
|
const value = args.shift(); if (!value || value.startsWith('-')) throw new Error(`Missing value for ${flag}`);
|
|
@@ -50,6 +52,9 @@ export function parseArgs(argv) {
|
|
|
50
52
|
result.filters[name] = value;
|
|
51
53
|
}
|
|
52
54
|
if (result.filters.source && !SOURCES.includes(result.filters.source)) throw new Error('Unknown source');
|
|
55
|
+
if (result.receipt && (command !== 'show' || !result.localOnly || !result.id.startsWith('plugin-tasks:'))) {
|
|
56
|
+
throw new Error('--receipt requires show <plugin-task-id> --local');
|
|
57
|
+
}
|
|
53
58
|
if (command === 'cancel' && (Object.keys(result.filters).length || result.localOnly)) throw new Error('cancel accepts only a local automation id and --json');
|
|
54
59
|
return result;
|
|
55
60
|
}
|
|
@@ -101,13 +106,17 @@ export async function run(argv = [], dependencies = {}) {
|
|
|
101
106
|
if (!result.ok) (dependencies.setExitCode || (code => { process.exitCode = code; }))(result.exit_code);
|
|
102
107
|
return result;
|
|
103
108
|
}
|
|
109
|
+
if (parsed.receipt && !process.stdin.isTTY) throw new Error('--receipt requires a local terminal');
|
|
104
110
|
const root = dependencies.packageRoot || process.env.TR_PACKAGE_ROOT;
|
|
105
111
|
if (!root) throw new Error('TR_PACKAGE_ROOT is required');
|
|
106
112
|
if (parsed.command === 'cancel') {
|
|
107
113
|
const result = await (dependencies.cancel || cancelAutomation)(root, parsed.id);
|
|
108
114
|
write(`${JSON.stringify(result)}\n`); return result;
|
|
109
115
|
}
|
|
110
|
-
let inventory = await (dependencies.inventory || meshAutomationInventory)(root, {
|
|
116
|
+
let inventory = await (dependencies.inventory || meshAutomationInventory)(root, {
|
|
117
|
+
localOnly: parsed.localOnly,
|
|
118
|
+
...(parsed.receipt ? { receiptId: parsed.id } : {}),
|
|
119
|
+
});
|
|
111
120
|
inventory = filterInventory(inventory, parsed.filters);
|
|
112
121
|
let result = inventory;
|
|
113
122
|
if (parsed.command === 'show') {
|
|
@@ -1,19 +1,19 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "tr-plugin-automations",
|
|
3
|
-
"version": "1.0
|
|
3
|
+
"version": "1.2.0",
|
|
4
4
|
"lockfileVersion": 3,
|
|
5
5
|
"requires": true,
|
|
6
6
|
"packages": {
|
|
7
7
|
"": {
|
|
8
8
|
"name": "tr-plugin-automations",
|
|
9
|
-
"version": "1.0
|
|
9
|
+
"version": "1.2.0",
|
|
10
10
|
"license": "MIT",
|
|
11
11
|
"dependencies": {
|
|
12
12
|
"@gregiteen/ssss-cli": "0.14.5"
|
|
13
13
|
},
|
|
14
14
|
"devDependencies": {
|
|
15
15
|
"jsdom": "^29.1.1",
|
|
16
|
-
"total-recall-brain": "3.
|
|
16
|
+
"total-recall-brain": "3.45.0",
|
|
17
17
|
"vitest": "^4.1.10"
|
|
18
18
|
}
|
|
19
19
|
},
|
|
@@ -7021,9 +7021,9 @@
|
|
|
7021
7021
|
}
|
|
7022
7022
|
},
|
|
7023
7023
|
"node_modules/total-recall-brain": {
|
|
7024
|
-
"version": "3.
|
|
7025
|
-
"resolved": "https://registry.npmjs.org/total-recall-brain/-/total-recall-brain-3.
|
|
7026
|
-
"integrity": "sha512-
|
|
7024
|
+
"version": "3.45.0",
|
|
7025
|
+
"resolved": "https://registry.npmjs.org/total-recall-brain/-/total-recall-brain-3.45.0.tgz",
|
|
7026
|
+
"integrity": "sha512-HDYfROazZbsLHQsFPnlBcSpe1HL1QEi7JG8x/eNRUI06RxVQsZWl8LwBo2lTWjWRDrKmCy7BUmSXQDuWF3lrEw==",
|
|
7027
7027
|
"dev": true,
|
|
7028
7028
|
"license": "MIT",
|
|
7029
7029
|
"workspaces": [
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "tr-plugin-automations",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.2.0",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "Scheduled plugin task runner plus automation sources, triggers, observed outcomes and coverage across the Total Recall mesh.",
|
|
6
6
|
"scripts": {
|
|
@@ -19,9 +19,10 @@
|
|
|
19
19
|
"cron.mjs",
|
|
20
20
|
"capability/",
|
|
21
21
|
"BRICK.md",
|
|
22
|
-
"
|
|
22
|
+
"DESIGN.md",
|
|
23
|
+
"ui/home.js",
|
|
23
24
|
"ui/automations.js",
|
|
24
|
-
"ui/
|
|
25
|
+
"ui/chunks/"
|
|
25
26
|
],
|
|
26
27
|
"publishConfig": {
|
|
27
28
|
"access": "public"
|
|
@@ -2,10 +2,14 @@
|
|
|
2
2
|
"$schema": "https://github.com/gregiteen/total-recall/blob/main/metadata.plugin.schema.json",
|
|
3
3
|
"id": "automations",
|
|
4
4
|
"name": "Automations",
|
|
5
|
-
"version": "1.
|
|
5
|
+
"version": "1.2.0",
|
|
6
6
|
"description": "Run scheduled plugin tasks and inspect automation sources, triggers, observed outcomes and coverage across the mesh.",
|
|
7
7
|
"author": "Total Recall",
|
|
8
8
|
"license": "MIT",
|
|
9
|
+
"reuse": {
|
|
10
|
+
"commands": ["total-recall mesh nodes"],
|
|
11
|
+
"owned": "Collects automation sources, triggers, outcomes and node coverage, and delegates confirmed local task cancellation to its owner."
|
|
12
|
+
},
|
|
9
13
|
"use_cases": [
|
|
10
14
|
"automation",
|
|
11
15
|
"monitoring"
|
|
@@ -43,7 +47,9 @@
|
|
|
43
47
|
"timeout_ms": 25000,
|
|
44
48
|
"effect": "read",
|
|
45
49
|
"output": "json",
|
|
46
|
-
"args": [
|
|
50
|
+
"args": [
|
|
51
|
+
{ "name": "receipt", "flag": "--receipt", "type": "boolean", "label": "Local terminal failure receipt" }
|
|
52
|
+
]
|
|
47
53
|
},
|
|
48
54
|
{
|
|
49
55
|
"name": "dream",
|
|
@@ -77,13 +83,14 @@
|
|
|
77
83
|
"daemon": ["scheduler"]
|
|
78
84
|
},
|
|
79
85
|
"ui": {
|
|
80
|
-
"design_tokens": "
|
|
86
|
+
"design_tokens": "DESIGN.md",
|
|
87
|
+
"home": "automations",
|
|
81
88
|
"elements": [
|
|
82
89
|
{
|
|
83
90
|
"id": "automations",
|
|
84
91
|
"kind": "panel",
|
|
85
92
|
"tag": "tr-automations",
|
|
86
|
-
"module": "ui/
|
|
93
|
+
"module": "ui/home.js",
|
|
87
94
|
"description": "Live automation inventory with per-source node coverage",
|
|
88
95
|
"events": [],
|
|
89
96
|
"tokens": [
|
|
@@ -97,29 +104,6 @@
|
|
|
97
104
|
"radius-md"
|
|
98
105
|
],
|
|
99
106
|
"optional_tokens": []
|
|
100
|
-
},
|
|
101
|
-
{
|
|
102
|
-
"id": "card",
|
|
103
|
-
"kind": "card",
|
|
104
|
-
"tag": "tr-automations-card",
|
|
105
|
-
"module": "ui/card.js",
|
|
106
|
-
"description": "Automations workspace"
|
|
107
|
-
}
|
|
108
|
-
]
|
|
109
|
-
},
|
|
110
|
-
"card_face": {
|
|
111
|
-
"skin": "standard",
|
|
112
|
-
"theme": "precision-chronometer",
|
|
113
|
-
"headline": "Automation sources, triggers and outcomes",
|
|
114
|
-
"primary_color": "#f2bd63",
|
|
115
|
-
"secondary_color": "#24221c",
|
|
116
|
-
"accent_color": "#f2bd63",
|
|
117
|
-
"touch_layout": "comfortable",
|
|
118
|
-
"interactive": true,
|
|
119
|
-
"quick_actions": [
|
|
120
|
-
{
|
|
121
|
-
"subcommand": "list",
|
|
122
|
-
"label": "Inspect automations"
|
|
123
107
|
}
|
|
124
108
|
]
|
|
125
109
|
},
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
/** External bundlers may use this entrypoint; the sandbox loads
|
|
2
|
-
export { AutomationsElement } from './
|
|
1
|
+
/** External bundlers may use this entrypoint; the sandbox loads the Home directly. */
|
|
2
|
+
export { AutomationsElement } from './home.js';
|