@bevel-software/platform-core-backend 0.26.0 → 0.27.0
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/agent-guide/access-control.md +17 -0
- package/agent-guide/conventions.md +8 -0
- package/agent-guide/html-views.md +83 -0
- package/agent-guide/new-knowledge-base.md +24 -0
- package/agent-guide/tool-manuals.md +10 -0
- package/dist/assets.d.ts +19 -0
- package/dist/assets.d.ts.map +1 -1
- package/dist/assets.js +26 -2
- package/dist/assets.js.map +1 -1
- package/dist/core/catalog-revision.d.ts +19 -1
- package/dist/core/catalog-revision.d.ts.map +1 -1
- package/dist/core/catalog-revision.js +14 -3
- package/dist/core/catalog-revision.js.map +1 -1
- package/dist/core/create-core-server.d.ts +5 -0
- package/dist/core/create-core-server.d.ts.map +1 -1
- package/dist/core/create-core-server.js +54 -3
- package/dist/core/create-core-server.js.map +1 -1
- package/dist/core/create-core-services.d.ts +26 -0
- package/dist/core/create-core-services.d.ts.map +1 -1
- package/dist/core/create-core-services.js +100 -8
- package/dist/core/create-core-services.js.map +1 -1
- package/dist/core/lifecycle.d.ts +16 -1
- package/dist/core/lifecycle.d.ts.map +1 -1
- package/dist/core/lifecycle.js +18 -1
- package/dist/core/lifecycle.js.map +1 -1
- package/dist/core-config.d.ts +21 -0
- package/dist/core-config.d.ts.map +1 -1
- package/dist/core-config.js +22 -1
- package/dist/core-config.js.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +2 -2
- package/dist/index.js.map +1 -1
- package/dist/modules/access/access-control.interface.d.ts +8 -0
- package/dist/modules/access/access-control.interface.d.ts.map +1 -1
- package/dist/modules/access/access-control.service.d.ts +1 -0
- package/dist/modules/access/access-control.service.d.ts.map +1 -1
- package/dist/modules/access/access-control.service.js +11 -0
- package/dist/modules/access/access-control.service.js.map +1 -1
- package/dist/modules/access/directory-sync-bot.js +1 -1
- package/dist/modules/access/directory-sync-bot.js.map +1 -1
- package/dist/modules/agent-guide/agent-guide.d.ts +6 -0
- package/dist/modules/agent-guide/agent-guide.d.ts.map +1 -1
- package/dist/modules/agent-guide/agent-guide.js +8 -0
- package/dist/modules/agent-guide/agent-guide.js.map +1 -1
- package/dist/modules/agent-guide/index.d.ts +1 -1
- package/dist/modules/agent-guide/index.d.ts.map +1 -1
- package/dist/modules/agent-guide/index.js +1 -1
- package/dist/modules/agent-guide/index.js.map +1 -1
- package/dist/modules/agent-instructions/compose.d.ts +5 -0
- package/dist/modules/agent-instructions/compose.d.ts.map +1 -1
- package/dist/modules/agent-instructions/compose.js +19 -2
- package/dist/modules/agent-instructions/compose.js.map +1 -1
- package/dist/modules/agent-instructions/shared-file-rules.js +19 -19
- package/dist/modules/agent-instructions/shared-file-rules.js.map +1 -1
- package/dist/modules/audit/agent-audit.service.d.ts +21 -2
- package/dist/modules/audit/agent-audit.service.d.ts.map +1 -1
- package/dist/modules/audit/agent-audit.service.js +43 -2
- package/dist/modules/audit/agent-audit.service.js.map +1 -1
- package/dist/modules/audit/agent-connection.routes.d.ts +34 -0
- package/dist/modules/audit/agent-connection.routes.d.ts.map +1 -0
- package/dist/modules/audit/agent-connection.routes.js +38 -0
- package/dist/modules/audit/agent-connection.routes.js.map +1 -0
- package/dist/modules/audit/audit.contract.d.ts +24 -0
- package/dist/modules/audit/audit.contract.d.ts.map +1 -1
- package/dist/modules/audit/audit.contract.js.map +1 -1
- package/dist/modules/audit/index.d.ts +1 -0
- package/dist/modules/audit/index.d.ts.map +1 -1
- package/dist/modules/audit/index.js +1 -0
- package/dist/modules/audit/index.js.map +1 -1
- package/dist/modules/auth/account.routes.d.ts.map +1 -1
- package/dist/modules/auth/account.routes.js +10 -3
- package/dist/modules/auth/account.routes.js.map +1 -1
- package/dist/modules/auth/auth.middleware.d.ts +7 -0
- package/dist/modules/auth/auth.middleware.d.ts.map +1 -1
- package/dist/modules/auth/auth.middleware.js +1 -1
- package/dist/modules/auth/auth.middleware.js.map +1 -1
- package/dist/modules/code-mode/code-mode.tool.d.ts.map +1 -1
- package/dist/modules/code-mode/code-mode.tool.js +11 -3
- package/dist/modules/code-mode/code-mode.tool.js.map +1 -1
- package/dist/modules/database/core-schema.d.ts +96 -0
- package/dist/modules/database/core-schema.d.ts.map +1 -1
- package/dist/modules/database/core-schema.js +32 -3
- package/dist/modules/database/core-schema.js.map +1 -1
- package/dist/modules/embed/account-link.service.d.ts +42 -0
- package/dist/modules/embed/account-link.service.d.ts.map +1 -0
- package/dist/modules/embed/account-link.service.js +50 -0
- package/dist/modules/embed/account-link.service.js.map +1 -0
- package/dist/modules/embed/embed-link.d.ts +58 -0
- package/dist/modules/embed/embed-link.d.ts.map +1 -0
- package/dist/modules/embed/embed-link.js +160 -0
- package/dist/modules/embed/embed-link.js.map +1 -0
- package/dist/modules/embed/embed.errors.d.ts +30 -0
- package/dist/modules/embed/embed.errors.d.ts.map +1 -0
- package/dist/modules/embed/embed.errors.js +42 -0
- package/dist/modules/embed/embed.errors.js.map +1 -0
- package/dist/modules/embed/embed.interface.d.ts +204 -0
- package/dist/modules/embed/embed.interface.d.ts.map +1 -0
- package/dist/modules/embed/embed.interface.js +2 -0
- package/dist/modules/embed/embed.interface.js.map +1 -0
- package/dist/modules/embed/embed.routes.d.ts +59 -0
- package/dist/modules/embed/embed.routes.d.ts.map +1 -0
- package/dist/modules/embed/embed.routes.js +343 -0
- package/dist/modules/embed/embed.routes.js.map +1 -0
- package/dist/modules/embed/embed.service.d.ts +169 -0
- package/dist/modules/embed/embed.service.d.ts.map +1 -0
- package/dist/modules/embed/embed.service.js +627 -0
- package/dist/modules/embed/embed.service.js.map +1 -0
- package/dist/modules/embed/embed.tools.d.ts +51 -0
- package/dist/modules/embed/embed.tools.d.ts.map +1 -0
- package/dist/modules/embed/embed.tools.js +170 -0
- package/dist/modules/embed/embed.tools.js.map +1 -0
- package/dist/modules/embed/mcp-app.d.ts +64 -0
- package/dist/modules/embed/mcp-app.d.ts.map +1 -0
- package/dist/modules/embed/mcp-app.js +147 -0
- package/dist/modules/embed/mcp-app.js.map +1 -0
- package/dist/modules/embed/mcp-app.routes.d.ts +21 -0
- package/dist/modules/embed/mcp-app.routes.d.ts.map +1 -0
- package/dist/modules/embed/mcp-app.routes.js +36 -0
- package/dist/modules/embed/mcp-app.routes.js.map +1 -0
- package/dist/modules/github-app/github-app.connection.d.ts +15 -0
- package/dist/modules/github-app/github-app.connection.d.ts.map +1 -1
- package/dist/modules/github-app/github-app.connection.js +34 -3
- package/dist/modules/github-app/github-app.connection.js.map +1 -1
- package/dist/modules/kb-fs/locking-filesystem.d.ts +65 -0
- package/dist/modules/kb-fs/locking-filesystem.d.ts.map +1 -1
- package/dist/modules/kb-fs/locking-filesystem.js +300 -0
- package/dist/modules/kb-fs/locking-filesystem.js.map +1 -1
- package/dist/modules/kb-sync/kb-sync.interface.d.ts +5 -0
- package/dist/modules/kb-sync/kb-sync.interface.d.ts.map +1 -1
- package/dist/modules/kb-sync/kb-sync.service.d.ts.map +1 -1
- package/dist/modules/kb-sync/kb-sync.service.js +6 -0
- package/dist/modules/kb-sync/kb-sync.service.js.map +1 -1
- package/dist/modules/mcp/mcp-auth.middleware.d.ts.map +1 -1
- package/dist/modules/mcp/mcp-auth.middleware.js +2 -1
- package/dist/modules/mcp/mcp-auth.middleware.js.map +1 -1
- package/dist/modules/mcp/mcp.service.d.ts +28 -1
- package/dist/modules/mcp/mcp.service.d.ts.map +1 -1
- package/dist/modules/mcp/mcp.service.js +64 -8
- package/dist/modules/mcp/mcp.service.js.map +1 -1
- package/dist/modules/mcp/oauth/bevel-oauth-provider.d.ts +24 -0
- package/dist/modules/mcp/oauth/bevel-oauth-provider.d.ts.map +1 -1
- package/dist/modules/mcp/oauth/bevel-oauth-provider.js +32 -4
- package/dist/modules/mcp/oauth/bevel-oauth-provider.js.map +1 -1
- package/dist/modules/onboarding/onboarding.contract.d.ts +80 -0
- package/dist/modules/onboarding/onboarding.contract.d.ts.map +1 -0
- package/dist/modules/onboarding/onboarding.contract.js +7 -0
- package/dist/modules/onboarding/onboarding.contract.js.map +1 -0
- package/dist/modules/onboarding/onboarding.routes.d.ts +18 -0
- package/dist/modules/onboarding/onboarding.routes.d.ts.map +1 -0
- package/dist/modules/onboarding/onboarding.routes.js +81 -0
- package/dist/modules/onboarding/onboarding.routes.js.map +1 -0
- package/dist/modules/onboarding/starter-pack.service.d.ts +213 -0
- package/dist/modules/onboarding/starter-pack.service.d.ts.map +1 -0
- package/dist/modules/onboarding/starter-pack.service.js +492 -0
- package/dist/modules/onboarding/starter-pack.service.js.map +1 -0
- package/dist/modules/onboarding/starter-packs.d.ts +78 -0
- package/dist/modules/onboarding/starter-packs.d.ts.map +1 -0
- package/dist/modules/onboarding/starter-packs.js +156 -0
- package/dist/modules/onboarding/starter-packs.js.map +1 -0
- package/dist/modules/plugins/index.d.ts +1 -1
- package/dist/modules/plugins/index.d.ts.map +1 -1
- package/dist/modules/plugins/index.js +1 -1
- package/dist/modules/plugins/index.js.map +1 -1
- package/dist/modules/plugins/plugin-provision.service.d.ts +19 -0
- package/dist/modules/plugins/plugin-provision.service.d.ts.map +1 -1
- package/dist/modules/plugins/plugin-provision.service.js +18 -1
- package/dist/modules/plugins/plugin-provision.service.js.map +1 -1
- package/dist/modules/plugins/plugins.routes.d.ts +0 -36
- package/dist/modules/plugins/plugins.routes.d.ts.map +1 -1
- package/dist/modules/plugins/plugins.routes.js +31 -0
- package/dist/modules/plugins/plugins.routes.js.map +1 -1
- package/dist/modules/settings/deployment-settings.service.d.ts +34 -0
- package/dist/modules/settings/deployment-settings.service.d.ts.map +1 -1
- package/dist/modules/settings/deployment-settings.service.js +134 -1
- package/dist/modules/settings/deployment-settings.service.js.map +1 -1
- package/dist/modules/settings/repository-source.d.ts +1 -0
- package/dist/modules/settings/repository-source.d.ts.map +1 -1
- package/dist/modules/settings/repository-source.js +3 -3
- package/dist/modules/settings/repository-source.js.map +1 -1
- package/dist/modules/skills/skills.tools.d.ts.map +1 -1
- package/dist/modules/skills/skills.tools.js +50 -32
- package/dist/modules/skills/skills.tools.js.map +1 -1
- package/dist/modules/tool-auth/connection-key-rejection.d.ts +10 -1
- package/dist/modules/tool-auth/connection-key-rejection.d.ts.map +1 -1
- package/dist/modules/tool-auth/connection-key-rejection.js +11 -3
- package/dist/modules/tool-auth/connection-key-rejection.js.map +1 -1
- package/dist/modules/tool-auth/external-api-key.interface.d.ts +8 -0
- package/dist/modules/tool-auth/external-api-key.interface.d.ts.map +1 -1
- package/dist/modules/tool-auth/external-api-key.service.d.ts +24 -2
- package/dist/modules/tool-auth/external-api-key.service.d.ts.map +1 -1
- package/dist/modules/tool-auth/external-api-key.service.js +59 -2
- package/dist/modules/tool-auth/external-api-key.service.js.map +1 -1
- package/dist/modules/tool-auth/tool-auth.middleware.d.ts.map +1 -1
- package/dist/modules/tool-auth/tool-auth.middleware.js +9 -4
- package/dist/modules/tool-auth/tool-auth.middleware.js.map +1 -1
- package/dist/modules/tool-helpers/index.d.ts +28 -1
- package/dist/modules/tool-helpers/index.d.ts.map +1 -1
- package/dist/modules/tool-helpers/index.js +28 -1
- package/dist/modules/tool-helpers/index.js.map +1 -1
- package/dist/modules/tool-helpers/route-argument-check.d.ts +10 -0
- package/dist/modules/tool-helpers/route-argument-check.d.ts.map +1 -0
- package/dist/modules/tool-helpers/route-argument-check.js +132 -0
- package/dist/modules/tool-helpers/route-argument-check.js.map +1 -0
- package/dist/modules/tool-helpers/route-tool-schemas.d.ts +89 -0
- package/dist/modules/tool-helpers/route-tool-schemas.d.ts.map +1 -0
- package/dist/modules/tool-helpers/route-tool-schemas.js +113 -0
- package/dist/modules/tool-helpers/route-tool-schemas.js.map +1 -0
- package/dist/modules/tool-helpers/tool-def.d.ts +71 -0
- package/dist/modules/tool-helpers/tool-def.d.ts.map +1 -1
- package/dist/modules/tool-helpers/tool-def.js +70 -6
- package/dist/modules/tool-helpers/tool-def.js.map +1 -1
- package/dist/modules/tool-helpers/tool-handler.d.ts +46 -6
- package/dist/modules/tool-helpers/tool-handler.d.ts.map +1 -1
- package/dist/modules/tool-helpers/tool-handler.js +157 -8
- package/dist/modules/tool-helpers/tool-handler.js.map +1 -1
- package/dist/modules/tool-helpers/tool.contract.d.ts +9 -0
- package/dist/modules/tool-helpers/tool.contract.d.ts.map +1 -1
- package/dist/modules/tool-helpers/tool.contract.js.map +1 -1
- package/dist/modules/tool-manuals/tool-manuals.tools.d.ts.map +1 -1
- package/dist/modules/tool-manuals/tool-manuals.tools.js +14 -5
- package/dist/modules/tool-manuals/tool-manuals.tools.js.map +1 -1
- package/dist/modules/tool-registry/description-length.d.ts +6 -2
- package/dist/modules/tool-registry/description-length.d.ts.map +1 -1
- package/dist/modules/tool-registry/description-length.js +27 -5
- package/dist/modules/tool-registry/description-length.js.map +1 -1
- package/dist/modules/tool-registry/guide-first.d.ts +4 -0
- package/dist/modules/tool-registry/guide-first.d.ts.map +1 -1
- package/dist/modules/tool-registry/guide-first.js +9 -1
- package/dist/modules/tool-registry/guide-first.js.map +1 -1
- package/dist/modules/workflow/agent-tools/change-request-read.tools.d.ts +53 -0
- package/dist/modules/workflow/agent-tools/change-request-read.tools.d.ts.map +1 -1
- package/dist/modules/workflow/agent-tools/change-request-read.tools.js +97 -68
- package/dist/modules/workflow/agent-tools/change-request-read.tools.js.map +1 -1
- package/dist/modules/workflow/agent-tools/workflow.tools.d.ts +8 -1
- package/dist/modules/workflow/agent-tools/workflow.tools.d.ts.map +1 -1
- package/dist/modules/workflow/agent-tools/workflow.tools.js +124 -37
- package/dist/modules/workflow/agent-tools/workflow.tools.js.map +1 -1
- package/dist/modules/workflow/file-lock.service.d.ts +29 -5
- package/dist/modules/workflow/file-lock.service.d.ts.map +1 -1
- package/dist/modules/workflow/file-lock.service.js +62 -5
- package/dist/modules/workflow/file-lock.service.js.map +1 -1
- package/dist/modules/workflow/git/git.service.d.ts +72 -1
- package/dist/modules/workflow/git/git.service.d.ts.map +1 -1
- package/dist/modules/workflow/git/git.service.js +172 -36
- package/dist/modules/workflow/git/git.service.js.map +1 -1
- package/dist/modules/workflow/git/node-git-runner.d.ts +15 -0
- package/dist/modules/workflow/git/node-git-runner.d.ts.map +1 -1
- package/dist/modules/workflow/git/node-git-runner.js +78 -6
- package/dist/modules/workflow/git/node-git-runner.js.map +1 -1
- package/dist/modules/workflow/pending-commits.service.d.ts +15 -0
- package/dist/modules/workflow/pending-commits.service.d.ts.map +1 -1
- package/dist/modules/workflow/pending-commits.service.js +25 -1
- package/dist/modules/workflow/pending-commits.service.js.map +1 -1
- package/dist/modules/workflow/pending-commits.worker.d.ts +6 -1
- package/dist/modules/workflow/pending-commits.worker.d.ts.map +1 -1
- package/dist/modules/workflow/pending-commits.worker.js +23 -6
- package/dist/modules/workflow/pending-commits.worker.js.map +1 -1
- package/dist/modules/workflow/recovery-bot.js +1 -1
- package/dist/modules/workflow/recovery-bot.js.map +1 -1
- package/dist/modules/workflow/review-workflow/review-workflow.service.d.ts.map +1 -1
- package/dist/modules/workflow/review-workflow/review-workflow.service.js +2 -1
- package/dist/modules/workflow/review-workflow/review-workflow.service.js.map +1 -1
- package/dist/modules/workflow/sanitize-error.d.ts +16 -0
- package/dist/modules/workflow/sanitize-error.d.ts.map +1 -1
- package/dist/modules/workflow/sanitize-error.js +45 -0
- package/dist/modules/workflow/sanitize-error.js.map +1 -1
- package/dist/modules/workflow/workflow.service.d.ts +183 -15
- package/dist/modules/workflow/workflow.service.d.ts.map +1 -1
- package/dist/modules/workflow/workflow.service.js +805 -106
- package/dist/modules/workflow/workflow.service.js.map +1 -1
- package/dist/modules/workspace/agent-download.builder.d.ts +105 -0
- package/dist/modules/workspace/agent-download.builder.d.ts.map +1 -0
- package/dist/modules/workspace/agent-download.builder.js +238 -0
- package/dist/modules/workspace/agent-download.builder.js.map +1 -0
- package/dist/modules/workspace/agent-download.routes.d.ts +77 -0
- package/dist/modules/workspace/agent-download.routes.d.ts.map +1 -0
- package/dist/modules/workspace/agent-download.routes.js +156 -0
- package/dist/modules/workspace/agent-download.routes.js.map +1 -0
- package/dist/modules/workspace/agent-download.store.d.ts +225 -0
- package/dist/modules/workspace/agent-download.store.d.ts.map +1 -0
- package/dist/modules/workspace/agent-download.store.js +423 -0
- package/dist/modules/workspace/agent-download.store.js.map +1 -0
- package/dist/modules/workspace/agent-upload.store.d.ts +10 -1
- package/dist/modules/workspace/agent-upload.store.d.ts.map +1 -1
- package/dist/modules/workspace/agent-upload.store.js +16 -6
- package/dist/modules/workspace/agent-upload.store.js.map +1 -1
- package/dist/modules/workspace/file-readers/raw-mime.d.ts +6 -0
- package/dist/modules/workspace/file-readers/raw-mime.d.ts.map +1 -0
- package/dist/modules/workspace/file-readers/raw-mime.js +38 -0
- package/dist/modules/workspace/file-readers/raw-mime.js.map +1 -0
- package/dist/modules/workspace/file-readers/text-reader.d.ts +5 -5
- package/dist/modules/workspace/file-readers/text-reader.d.ts.map +1 -1
- package/dist/modules/workspace/file-readers/text-reader.js +5 -8
- package/dist/modules/workspace/file-readers/text-reader.js.map +1 -1
- package/dist/modules/workspace/first-run.d.ts +111 -0
- package/dist/modules/workspace/first-run.d.ts.map +1 -0
- package/dist/modules/workspace/first-run.js +181 -0
- package/dist/modules/workspace/first-run.js.map +1 -0
- package/dist/modules/workspace/move-links.d.ts +92 -0
- package/dist/modules/workspace/move-links.d.ts.map +1 -0
- package/dist/modules/workspace/move-links.js +173 -0
- package/dist/modules/workspace/move-links.js.map +1 -0
- package/dist/modules/workspace/startup/steps/seed-tree.d.ts.map +1 -1
- package/dist/modules/workspace/startup/steps/seed-tree.js +3 -13
- package/dist/modules/workspace/startup/steps/seed-tree.js.map +1 -1
- package/dist/modules/workspace/workspace.routes.d.ts.map +1 -1
- package/dist/modules/workspace/workspace.routes.js +63 -22
- package/dist/modules/workspace/workspace.routes.js.map +1 -1
- package/dist/modules/workspace/workspace.service.d.ts +75 -2
- package/dist/modules/workspace/workspace.service.d.ts.map +1 -1
- package/dist/modules/workspace/workspace.service.js +197 -24
- package/dist/modules/workspace/workspace.service.js.map +1 -1
- package/dist/modules/workspace/workspace.tools.d.ts +59 -1
- package/dist/modules/workspace/workspace.tools.d.ts.map +1 -1
- package/dist/modules/workspace/workspace.tools.js +443 -65
- package/dist/modules/workspace/workspace.tools.js.map +1 -1
- package/dist/modules/write-access/write-access.d.ts.map +1 -1
- package/dist/modules/write-access/write-access.js +9 -0
- package/dist/modules/write-access/write-access.js.map +1 -1
- package/dist/shared/domain-errors.d.ts +73 -1
- package/dist/shared/domain-errors.d.ts.map +1 -1
- package/dist/shared/domain-errors.js +86 -12
- package/dist/shared/domain-errors.js.map +1 -1
- package/dist/shared/git.contract.d.ts +10 -1
- package/dist/shared/git.contract.d.ts.map +1 -1
- package/dist/shared/git.contract.js.map +1 -1
- package/dist/shared/utf8-text.d.ts +15 -0
- package/dist/shared/utf8-text.d.ts.map +1 -0
- package/dist/shared/utf8-text.js +20 -0
- package/dist/shared/utf8-text.js.map +1 -0
- package/dist/tenancy/static-tenant-source.d.ts +2 -1
- package/dist/tenancy/static-tenant-source.d.ts.map +1 -1
- package/dist/tenancy/static-tenant-source.js +9 -2
- package/dist/tenancy/static-tenant-source.js.map +1 -1
- package/mcp-app/page.html +349 -0
- package/migrations/0017_atlassian_account_links.sql +37 -0
- package/migrations/meta/0017_snapshot.json +2396 -0
- package/migrations/meta/_journal.json +8 -1
- package/package.json +5 -3
- package/src/__tests__/packaged-assets-ship.test.ts +16 -4
- package/src/assets.ts +28 -2
- package/src/core/__tests__/catalog-revision.test.ts +40 -0
- package/src/core/__tests__/gated-boot.test.ts +1 -0
- package/src/core/__tests__/lifecycle.test.ts +14 -0
- package/src/core/catalog-revision.ts +15 -2
- package/src/core/create-core-server.ts +67 -3
- package/src/core/create-core-services.ts +140 -6
- package/src/core/lifecycle.ts +28 -2
- package/src/core-config.ts +24 -1
- package/src/index.ts +2 -2
- package/src/modules/access/__tests__/access-control.service.test.ts +19 -0
- package/src/modules/access/access-control.interface.ts +13 -0
- package/src/modules/access/access-control.service.ts +16 -0
- package/src/modules/access/directory-sync-bot.ts +1 -1
- package/src/modules/agent-guide/__tests__/agent-guide.test.ts +58 -0
- package/src/modules/agent-guide/__tests__/agent-guide.tools.test.ts +19 -1
- package/src/modules/agent-guide/agent-guide.ts +9 -0
- package/src/modules/agent-guide/index.ts +1 -0
- package/src/modules/agent-instructions/__tests__/shared-file-rules.test.ts +14 -0
- package/src/modules/agent-instructions/compose.ts +17 -2
- package/src/modules/agent-instructions/shared-file-rules.ts +19 -19
- package/src/modules/audit/__tests__/agent-audit.service.test.ts +64 -4
- package/src/modules/audit/__tests__/agent-connection.routes.test.ts +102 -0
- package/src/modules/audit/agent-audit.service.ts +58 -3
- package/src/modules/audit/agent-connection.routes.ts +56 -0
- package/src/modules/audit/audit.contract.ts +26 -0
- package/src/modules/audit/index.ts +1 -0
- package/src/modules/auth/__tests__/account.routes.test.ts +5 -3
- package/src/modules/auth/account.routes.ts +10 -3
- package/src/modules/auth/auth.middleware.ts +1 -1
- package/src/modules/code-mode/__tests__/code-mode.tool.test.ts +18 -2
- package/src/modules/code-mode/code-mode.tool.ts +13 -2
- package/src/modules/database/core-schema.ts +33 -3
- package/src/modules/embed/__tests__/account-links.migration.test.ts +98 -0
- package/src/modules/embed/__tests__/embed-link.test.ts +122 -0
- package/src/modules/embed/__tests__/embed.routes.test.ts +362 -0
- package/src/modules/embed/__tests__/embed.service.lock.test.ts +193 -0
- package/src/modules/embed/__tests__/embed.service.test.ts +805 -0
- package/src/modules/embed/__tests__/embed.tools.test.ts +304 -0
- package/src/modules/embed/__tests__/mcp-app.test.ts +207 -0
- package/src/modules/embed/account-link.service.ts +76 -0
- package/src/modules/embed/embed-link.ts +180 -0
- package/src/modules/embed/embed.errors.ts +43 -0
- package/src/modules/embed/embed.interface.ts +203 -0
- package/src/modules/embed/embed.routes.ts +363 -0
- package/src/modules/embed/embed.service.ts +705 -0
- package/src/modules/embed/embed.tools.ts +206 -0
- package/src/modules/embed/mcp-app.routes.ts +41 -0
- package/src/modules/embed/mcp-app.ts +173 -0
- package/src/modules/github-app/__tests__/github-app.test.ts +76 -0
- package/src/modules/github-app/github-app.connection.ts +38 -4
- package/src/modules/kb-fs/__tests__/move-with-edits.test.ts +304 -0
- package/src/modules/kb-fs/locking-filesystem.ts +287 -0
- package/src/modules/kb-sync/__tests__/kb-sync.service.test.ts +35 -0
- package/src/modules/kb-sync/kb-sync.interface.ts +2 -0
- package/src/modules/kb-sync/kb-sync.service.ts +6 -0
- package/src/modules/mcp/__tests__/bevel-oauth-provider.test.ts +68 -11
- package/src/modules/mcp/__tests__/mcp-proxy-helpers.test.ts +37 -2
- package/src/modules/mcp/__tests__/mcp.app.e2e.test.ts +200 -0
- package/src/modules/mcp/__tests__/mcp.e2e.test.ts +3 -1
- package/src/modules/mcp/__tests__/mcp.service.test.ts +23 -13
- package/src/modules/mcp/__tests__/tool-call-interface.e2e.test.ts +499 -0
- package/src/modules/mcp/mcp-auth.middleware.ts +2 -1
- package/src/modules/mcp/mcp.service.ts +81 -12
- package/src/modules/mcp/oauth/bevel-oauth-provider.ts +42 -4
- package/src/modules/onboarding/__tests__/onboarding.routes.test.ts +163 -0
- package/src/modules/onboarding/__tests__/starter-pack.service.test.ts +635 -0
- package/src/modules/onboarding/__tests__/starter-packs.test.ts +169 -0
- package/src/modules/onboarding/onboarding.contract.ts +85 -0
- package/src/modules/onboarding/onboarding.routes.ts +85 -0
- package/src/modules/onboarding/starter-pack.service.ts +580 -0
- package/src/modules/onboarding/starter-packs.ts +182 -0
- package/src/modules/plugins/__tests__/plugins.tools.test.ts +25 -2
- package/src/modules/plugins/index.ts +1 -0
- package/src/modules/plugins/plugin-provision.service.ts +22 -1
- package/src/modules/plugins/plugins.routes.ts +29 -0
- package/src/modules/settings/__tests__/deployment-settings.service.test.ts +150 -1
- package/src/modules/settings/__tests__/repository-source.test.ts +9 -0
- package/src/modules/settings/deployment-settings.service.ts +131 -1
- package/src/modules/settings/repository-source.ts +4 -4
- package/src/modules/skills/__tests__/skills.tools.description.test.ts +5 -1
- package/src/modules/skills/skills.tools.ts +55 -35
- package/src/modules/tool-auth/__tests__/connection-key-rejection.test.ts +32 -0
- package/src/modules/tool-auth/__tests__/external-api-key.service.test.ts +65 -0
- package/src/modules/tool-auth/connection-key-rejection.ts +13 -3
- package/src/modules/tool-auth/external-api-key.interface.ts +9 -0
- package/src/modules/tool-auth/external-api-key.service.ts +61 -4
- package/src/modules/tool-auth/tool-auth.middleware.ts +13 -4
- package/src/modules/tool-helpers/__tests__/branch-declaration.test.ts +502 -0
- package/src/modules/tool-helpers/__tests__/route-argument-check.test.ts +337 -0
- package/src/modules/tool-helpers/index.ts +34 -1
- package/src/modules/tool-helpers/route-argument-check.ts +149 -0
- package/src/modules/tool-helpers/route-tool-schemas.ts +171 -0
- package/src/modules/tool-helpers/tool-def.ts +132 -7
- package/src/modules/tool-helpers/tool-handler.ts +196 -8
- package/src/modules/tool-helpers/tool.contract.ts +9 -0
- package/src/modules/tool-manuals/tool-manuals.tools.ts +15 -5
- package/src/modules/tool-registry/__tests__/own-tool-schemas.test.ts +14 -1
- package/src/modules/tool-registry/__tests__/tool-description-length.test.ts +23 -10
- package/src/modules/tool-registry/description-length.ts +34 -7
- package/src/modules/tool-registry/guide-first.ts +8 -1
- package/src/modules/workflow/__tests__/file-lock.service.deletion-gate.test.ts +104 -0
- package/src/modules/workflow/__tests__/pending-commits.repository-replaced.test.ts +66 -0
- package/src/modules/workflow/__tests__/pending-commits.worker.test.ts +31 -2
- package/src/modules/workflow/__tests__/preserve-roles-yaml.test.ts +110 -6
- package/src/modules/workflow/__tests__/sanitize-error.test.ts +89 -1
- package/src/modules/workflow/__tests__/workflow.routes.push-refused.test.ts +202 -0
- package/src/modules/workflow/__tests__/workflow.service.branch-in-use.test.ts +6 -6
- package/src/modules/workflow/__tests__/workflow.service.delete-branch.test.ts +1026 -0
- package/src/modules/workflow/__tests__/workflow.service.facade.test.ts +468 -10
- package/src/modules/workflow/__tests__/workflow.service.folder-proposals.test.ts +4 -0
- package/src/modules/workflow/__tests__/workflow.service.releaseLock.test.ts +5 -4
- package/src/modules/workflow/__tests__/workflow.service.update-from-target.test.ts +54 -2
- package/src/modules/workflow/agent-tools/__tests__/change-request-read.tools.test.ts +41 -5
- package/src/modules/workflow/agent-tools/__tests__/workflow.tools.test.ts +127 -2
- package/src/modules/workflow/agent-tools/change-request-read.tools.ts +157 -122
- package/src/modules/workflow/agent-tools/workflow.tools.ts +129 -35
- package/src/modules/workflow/file-lock.service.ts +67 -5
- package/src/modules/workflow/git/__tests__/git.service.deleteBranch.test.ts +164 -0
- package/src/modules/workflow/git/__tests__/git.service.pull.test.ts +48 -1
- package/src/modules/workflow/git/__tests__/node-git-runner.test.ts +231 -2
- package/src/modules/workflow/git/git.service.ts +176 -38
- package/src/modules/workflow/git/node-git-runner.ts +82 -7
- package/src/modules/workflow/pending-commits.service.ts +29 -1
- package/src/modules/workflow/pending-commits.worker.ts +24 -6
- package/src/modules/workflow/recovery-bot.ts +1 -1
- package/src/modules/workflow/review-workflow/review-workflow.service.ts +2 -1
- package/src/modules/workflow/sanitize-error.ts +50 -0
- package/src/modules/workflow/workflow.service.ts +879 -112
- package/src/modules/workspace/__tests__/agent-downloads.test.ts +823 -0
- package/src/modules/workspace/__tests__/first-run.test.ts +234 -0
- package/src/modules/workspace/__tests__/git-internals.security.test.ts +5 -2
- package/src/modules/workspace/__tests__/md-links.test.ts +353 -0
- package/src/modules/workspace/__tests__/move-links.test.ts +261 -0
- package/src/modules/workspace/__tests__/rest-tool-arguments.test.ts +219 -0
- package/src/modules/workspace/__tests__/workspace-paths-inside-the-repo.test.ts +3 -0
- package/src/modules/workspace/__tests__/workspace.routes.delete.test.ts +102 -0
- package/src/modules/workspace/__tests__/workspace.routes.download.test.ts +52 -5
- package/src/modules/workspace/__tests__/workspace.routes.folder-zip-access.test.ts +190 -0
- package/src/modules/workspace/__tests__/workspace.service.forget-clone-races.test.ts +8 -4
- package/src/modules/workspace/__tests__/workspace.service.test.ts +50 -8
- package/src/modules/workspace/__tests__/workspace.tools.branch-errors.test.ts +44 -1
- package/src/modules/workspace/__tests__/workspace.tools.test.ts +409 -12
- package/src/modules/workspace/agent-download.builder.ts +308 -0
- package/src/modules/workspace/agent-download.routes.ts +183 -0
- package/src/modules/workspace/agent-download.store.ts +533 -0
- package/src/modules/workspace/agent-upload.store.ts +23 -7
- package/src/modules/workspace/file-readers/raw-mime.ts +40 -0
- package/src/modules/workspace/file-readers/text-reader.ts +5 -8
- package/src/modules/workspace/first-run.ts +222 -0
- package/src/modules/workspace/move-links.ts +237 -0
- package/src/modules/workspace/startup/steps/seed-tree.ts +3 -12
- package/src/modules/workspace/workspace.routes.ts +64 -22
- package/src/modules/workspace/workspace.service.ts +202 -25
- package/src/modules/workspace/workspace.tools.ts +492 -63
- package/src/modules/write-access/__tests__/write-access.test.ts +13 -0
- package/src/modules/write-access/write-access.ts +9 -0
- package/src/shared/domain-errors.ts +108 -11
- package/src/shared/git.contract.ts +8 -1
- package/src/shared/utf8-text.ts +21 -0
- package/src/tenancy/__tests__/static-tenant-source.test.ts +1 -0
- package/src/tenancy/static-tenant-source.ts +10 -2
- package/starter-packs/README.md +103 -0
- package/starter-packs/engineering/KnowledgeBase/About us.md +9 -0
- package/starter-packs/engineering/KnowledgeBase/Architecture.md +9 -0
- package/starter-packs/engineering/KnowledgeBase/Glossary.md +9 -0
- package/starter-packs/engineering/KnowledgeBase/How we ship.md +9 -0
- package/starter-packs/engineering/Plugins/engineering-starter/LICENSE +21 -0
- package/starter-packs/engineering/Plugins/engineering-starter/SOURCE.md +20 -0
- package/starter-packs/engineering/Plugins/engineering-starter/access.md +19 -0
- package/starter-packs/engineering/Plugins/engineering-starter/plugin.json +10 -0
- package/starter-packs/engineering/Plugins/engineering-starter/skills/office-hours/SKILL.md +171 -0
- package/starter-packs/engineering/Plugins/engineering-starter/skills/office-hours/sections/phase-2a-startup-diagnostic.md +157 -0
- package/starter-packs/engineering/Plugins/engineering-starter/skills/office-hours/sections/phase-2b-builder-brainstorm.md +39 -0
- package/starter-packs/engineering/Plugins/engineering-starter/skills/plan-ceo-review/SKILL.md +144 -0
- package/starter-packs/engineering/Plugins/engineering-starter/skills/plan-eng-review/SKILL.md +144 -0
- package/starter-packs/engineering/Plugins/engineering-starter/skills/review/SKILL.md +80 -0
- package/starter-packs/engineering/Plugins/engineering-starter/skills/review/checklist.md +184 -0
- package/starter-packs/engineering/pack.yaml +11 -0
- package/starter-packs/general/KnowledgeBase/About us.md +9 -0
- package/starter-packs/general/KnowledgeBase/Glossary.md +9 -0
- package/starter-packs/general/KnowledgeBase/How we work.md +9 -0
- package/starter-packs/general/Plugins/general-starter/LICENSE +202 -0
- package/starter-packs/general/Plugins/general-starter/SOURCE.md +10 -0
- package/starter-packs/general/Plugins/general-starter/access.md +19 -0
- package/starter-packs/general/Plugins/general-starter/plugin.json +10 -0
- package/starter-packs/general/Plugins/general-starter/skills/memory-management/SKILL.md +332 -0
- package/starter-packs/general/Plugins/general-starter/skills/productivity-start/SKILL.md +163 -0
- package/starter-packs/general/Plugins/general-starter/skills/productivity-update/SKILL.md +167 -0
- package/starter-packs/general/Plugins/general-starter/skills/task-management/SKILL.md +83 -0
- package/starter-packs/general/pack.yaml +10 -0
- package/starter-packs/operations/KnowledgeBase/Glossary.md +9 -0
- package/starter-packs/operations/KnowledgeBase/How we work.md +9 -0
- package/starter-packs/operations/KnowledgeBase/Processes.md +9 -0
- package/starter-packs/operations/KnowledgeBase/Tools we use.md +9 -0
- package/starter-packs/operations/KnowledgeBase/Vendors.md +9 -0
- package/starter-packs/operations/Plugins/operations-starter/LICENSE +202 -0
- package/starter-packs/operations/Plugins/operations-starter/SOURCE.md +10 -0
- package/starter-packs/operations/Plugins/operations-starter/access.md +19 -0
- package/starter-packs/operations/Plugins/operations-starter/plugin.json +10 -0
- package/starter-packs/operations/Plugins/operations-starter/skills/capacity-plan/SKILL.md +111 -0
- package/starter-packs/operations/Plugins/operations-starter/skills/change-request/SKILL.md +119 -0
- package/starter-packs/operations/Plugins/operations-starter/skills/compliance-tracking/SKILL.md +44 -0
- package/starter-packs/operations/Plugins/operations-starter/skills/process-doc/SKILL.md +80 -0
- package/starter-packs/operations/Plugins/operations-starter/skills/process-optimization/SKILL.md +39 -0
- package/starter-packs/operations/Plugins/operations-starter/skills/risk-assessment/SKILL.md +40 -0
- package/starter-packs/operations/Plugins/operations-starter/skills/runbook/SKILL.md +85 -0
- package/starter-packs/operations/Plugins/operations-starter/skills/status-report/SKILL.md +75 -0
- package/starter-packs/operations/Plugins/operations-starter/skills/vendor-review/SKILL.md +102 -0
- package/starter-packs/operations/pack.yaml +12 -0
- package/starter-packs/sales/KnowledgeBase/About us.md +9 -0
- package/starter-packs/sales/KnowledgeBase/Customers.md +9 -0
- package/starter-packs/sales/KnowledgeBase/Glossary.md +9 -0
- package/starter-packs/sales/KnowledgeBase/How we sell.md +9 -0
- package/starter-packs/sales/KnowledgeBase/Objections.md +9 -0
- package/starter-packs/sales/KnowledgeBase/Pricing.md +9 -0
- package/starter-packs/sales/Plugins/sales-starter/LICENSE +202 -0
- package/starter-packs/sales/Plugins/sales-starter/SOURCE.md +10 -0
- package/starter-packs/sales/Plugins/sales-starter/access.md +19 -0
- package/starter-packs/sales/Plugins/sales-starter/plugin.json +10 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/account-context/SKILL.md +94 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/account-plan/SKILL.md +95 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/account-research/SKILL.md +99 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/account-tiering/SKILL.md +101 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/call-prep/SKILL.md +111 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/call-summary/SKILL.md +111 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/close-plan/SKILL.md +106 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/competitive-intelligence/SKILL.md +102 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/create-an-asset/SKILL.md +105 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/crm-hygiene-check/SKILL.md +103 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/customer-health/SKILL.md +108 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/customer-voice/SKILL.md +94 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/daily-briefing/SKILL.md +61 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/deal-advance-gap/SKILL.md +102 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/deal-review/SKILL.md +105 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/deal-signals/SKILL.md +96 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/deal-slip-scenario/SKILL.md +104 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/draft-outreach/SKILL.md +116 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/end-of-day/SKILL.md +114 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/expansion-whitespace/SKILL.md +97 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/forecast/SKILL.md +100 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/handle-objection/SKILL.md +93 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/inbox-sweep/SKILL.md +114 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/lead-triage/SKILL.md +106 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/log-activity/SKILL.md +111 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/pipeline-review/SKILL.md +97 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/renewal-radar/SKILL.md +95 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/rep-context/SKILL.md +90 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/route-lead/SKILL.md +111 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/sales-setup/SKILL.md +200 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/schedule-meeting/SKILL.md +99 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/stakeholder-map/SKILL.md +107 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/team-pipeline/SKILL.md +105 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/update-opportunity/SKILL.md +112 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/weekly-wrap/SKILL.md +90 -0
- package/starter-packs/sales/Plugins/sales-starter/skills/win-loss-review/SKILL.md +88 -0
- package/starter-packs/sales/pack.yaml +13 -0
- package/starter-packs/support/KnowledgeBase/Escalations.md +9 -0
- package/starter-packs/support/KnowledgeBase/Glossary.md +9 -0
- package/starter-packs/support/KnowledgeBase/Known issues.md +9 -0
- package/starter-packs/support/KnowledgeBase/Products.md +9 -0
- package/starter-packs/support/KnowledgeBase/Tone of voice.md +9 -0
- package/starter-packs/support/Plugins/support-starter/LICENSE +202 -0
- package/starter-packs/support/Plugins/support-starter/SOURCE.md +10 -0
- package/starter-packs/support/Plugins/support-starter/access.md +19 -0
- package/starter-packs/support/Plugins/support-starter/plugin.json +10 -0
- package/starter-packs/support/Plugins/support-starter/skills/customer-escalation/SKILL.md +246 -0
- package/starter-packs/support/Plugins/support-starter/skills/customer-research/SKILL.md +250 -0
- package/starter-packs/support/Plugins/support-starter/skills/draft-response/SKILL.md +416 -0
- package/starter-packs/support/Plugins/support-starter/skills/kb-article/SKILL.md +350 -0
- package/starter-packs/support/Plugins/support-starter/skills/ticket-triage/SKILL.md +273 -0
- package/starter-packs/support/pack.yaml +12 -0
|
@@ -0,0 +1,180 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A knowledge-base reference resolved from whatever a consumer hands the
|
|
3
|
+
* mint: a pasted app URL, a repo-relative path, or a bare node id.
|
|
4
|
+
*
|
|
5
|
+
* Two consumers share this grammar and must keep sharing it — the MCP
|
|
6
|
+
* `open_page` tool (a path, from a model) and the Atlassian connector (a
|
|
7
|
+
* `content:` marker, from a person pasting into a ticket). The mint contract
|
|
8
|
+
* is the boundary between Hexis and that connector's own repository, so this
|
|
9
|
+
* parse is the one part of the embed that may not change shape.
|
|
10
|
+
*/
|
|
11
|
+
|
|
12
|
+
/** A reference to a FILE, and optionally one heading inside it. */
|
|
13
|
+
export interface EmbedRef {
|
|
14
|
+
/** Repo-relative path, e.g. `Product/Knowledge/Thing.md`. */
|
|
15
|
+
repoRelative: string;
|
|
16
|
+
/** Heading anchor slug (e.g. `problem-statement`), or undefined for the whole file. */
|
|
17
|
+
slug?: string;
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
/**
|
|
21
|
+
* A node-id reference — the canonical copy-link form `/workspace/<branch>/<id>`.
|
|
22
|
+
* Core has no node graph to resolve an id with, so it is handed back for a
|
|
23
|
+
* deployment that does (see `EmbedNodeIdResolver`); without one the mint
|
|
24
|
+
* refuses it the way it refuses any unresolvable reference.
|
|
25
|
+
*/
|
|
26
|
+
export interface EmbedIdRef {
|
|
27
|
+
nodeId: string;
|
|
28
|
+
slug?: string;
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
/** A node frontmatter id: lowercase alphanumeric + hyphens, no separators/dots. */
|
|
32
|
+
const NODE_ID_RE = /^[a-z0-9][a-z0-9-]*$/;
|
|
33
|
+
|
|
34
|
+
/** Thrown when a reference can't be parsed into a safe path or an id. */
|
|
35
|
+
export class EmbedRefParseError extends Error {
|
|
36
|
+
constructor(message: string) {
|
|
37
|
+
super(message);
|
|
38
|
+
this.name = 'EmbedRefParseError';
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
/** `decodeURIComponent` that turns a malformed escape into a parse error. */
|
|
43
|
+
function safeDecode(s: string): string {
|
|
44
|
+
try {
|
|
45
|
+
return decodeURIComponent(s);
|
|
46
|
+
} catch {
|
|
47
|
+
throw new EmbedRefParseError('Malformed percent-encoding in reference');
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
/**
|
|
52
|
+
* A safe repo-relative embeddable path: rejects absolute paths, traversal,
|
|
53
|
+
* control characters and percent-encoded separators.
|
|
54
|
+
*
|
|
55
|
+
* Deliberately NO extension allowlist. The enterprise panel this grammar came
|
|
56
|
+
* from accepted `.md`, `.html` and `.htm` only, because those were the two
|
|
57
|
+
* things its own renderer could draw. The embed now renders with the APP's
|
|
58
|
+
* renderer for the file's type — every type the app renders, documents and
|
|
59
|
+
* images included — so an extension list here would be a second, narrower
|
|
60
|
+
* answer to "what can be shown", and the one that is wrong.
|
|
61
|
+
*/
|
|
62
|
+
export function isSafeRepoRelativeEmbedPath(repoRelative: string): boolean {
|
|
63
|
+
if (!repoRelative) return false;
|
|
64
|
+
// eslint-disable-next-line no-control-regex
|
|
65
|
+
if (/[\x00-\x1f\x7f]/.test(repoRelative)) return false;
|
|
66
|
+
if (/%2e|%2f|%5c/i.test(repoRelative)) return false;
|
|
67
|
+
// A backslash is refused, not read as a separator: the workspace path
|
|
68
|
+
// validator refuses it too, so normalising it here would only move a
|
|
69
|
+
// malformed reference from this 400 to a later one.
|
|
70
|
+
if (repoRelative.includes('\\')) return false;
|
|
71
|
+
const norm = repoRelative;
|
|
72
|
+
if (norm.startsWith('/')) return false;
|
|
73
|
+
return norm.split('/').every((seg) => seg !== '' && seg !== '.' && seg !== '..');
|
|
74
|
+
}
|
|
75
|
+
|
|
76
|
+
/**
|
|
77
|
+
* Whether a reference that parses as a safe path should instead be read as a
|
|
78
|
+
* node id.
|
|
79
|
+
*
|
|
80
|
+
* With the extension allowlist gone, `my-process` is BOTH a legal path and a
|
|
81
|
+
* legal id, so the two forms need a rule rather than a fallback. The rule is
|
|
82
|
+
* the shape the copy-link produces: an id is one segment with no dot in it
|
|
83
|
+
* (`/workspace/<branch>/<id>`). Anything with a separator or an extension is
|
|
84
|
+
* a path, which is every real file in the repository.
|
|
85
|
+
*/
|
|
86
|
+
function looksLikeNodeId(repoRelative: string): boolean {
|
|
87
|
+
return !repoRelative.includes('/') && !repoRelative.includes('.') && NODE_ID_RE.test(repoRelative);
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
/**
|
|
91
|
+
* A separator spelled `%2F` or `%5C` is refused BEFORE decoding: decoded, it
|
|
92
|
+
* becomes a real `/` that the safe-path check can no longer tell from one
|
|
93
|
+
* the caller wrote, and `Data%2FThing.md` would name `Data/Thing.md`.
|
|
94
|
+
*/
|
|
95
|
+
function refuseEncodedSeparators(rawPath: string): void {
|
|
96
|
+
if (/%2f|%5c/i.test(rawPath)) {
|
|
97
|
+
throw new EmbedRefParseError(`Not a safe knowledge-base path: ${rawPath}`);
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
/**
|
|
102
|
+
* Parse a reference into a file path or a node id. Accepts:
|
|
103
|
+
* - A full app URL: `https://<host>/workspace/<branch>/<kbDir>/<path>#<slug>`
|
|
104
|
+
* (also `/embed/<branch>/…`), optionally angle-bracketed and/or
|
|
105
|
+
* `content:`-prefixed.
|
|
106
|
+
* - A bare path, with or without a fragment: `<kbDir>/<path>#<slug>`,
|
|
107
|
+
* `<path>#<slug>`, or just `<path>` (whole file).
|
|
108
|
+
* - A bare node id (the copy-link form).
|
|
109
|
+
*
|
|
110
|
+
* The branch segment in a URL is intentionally ignored: the editable embed
|
|
111
|
+
* always targets the deployment's default branch. A missing `#slug` means
|
|
112
|
+
* "the whole file".
|
|
113
|
+
*/
|
|
114
|
+
export function parseEmbedRef(raw: string, kbDirName: string): EmbedRef | EmbedIdRef {
|
|
115
|
+
if (typeof raw !== 'string' || raw.trim() === '') {
|
|
116
|
+
throw new EmbedRefParseError('Empty reference');
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
// A person pastes the marker, so the two decorations arrive in either order
|
|
120
|
+
// — `content: <url>` and `<content: url>` are both things a ticket holds.
|
|
121
|
+
// Peeled in a loop rather than in one fixed order, so neither spelling
|
|
122
|
+
// leaves a `content:` prefix inside the path (where it reads as a scheme and
|
|
123
|
+
// the whole reference is refused).
|
|
124
|
+
let ref = raw.trim();
|
|
125
|
+
for (let i = 0; i < 4; i += 1) {
|
|
126
|
+
const peeled = ref
|
|
127
|
+
.replace(/^content:\s*/i, '')
|
|
128
|
+
.replace(/^<+/, '')
|
|
129
|
+
.replace(/>+$/, '')
|
|
130
|
+
.trim();
|
|
131
|
+
if (peeled === ref) break;
|
|
132
|
+
ref = peeled;
|
|
133
|
+
}
|
|
134
|
+
|
|
135
|
+
let pathPart: string;
|
|
136
|
+
let fragment: string;
|
|
137
|
+
|
|
138
|
+
if (/^https?:\/\//i.test(ref)) {
|
|
139
|
+
let url: URL;
|
|
140
|
+
try {
|
|
141
|
+
url = new URL(ref);
|
|
142
|
+
} catch {
|
|
143
|
+
throw new EmbedRefParseError(`Not a valid URL: ${ref}`);
|
|
144
|
+
}
|
|
145
|
+
fragment = safeDecode(url.hash.replace(/^#/, ''));
|
|
146
|
+
// The app's route (`workspace` or `embed`) is found wherever it sits: a
|
|
147
|
+
// deployment served under a path prefix carries it after the prefix,
|
|
148
|
+
// which is then not part of the file's path. The branch segment that
|
|
149
|
+
// follows it is ignored — and may carry an encoded separator, since a
|
|
150
|
+
// default branch named `team/main` is written `team%2Fmain` there; only
|
|
151
|
+
// the FILE path after it is held to the plain-separator rule.
|
|
152
|
+
const rawSegments = url.pathname.split('/').filter(Boolean);
|
|
153
|
+
// Matched DECODED (a route name may arrive percent-encoded), while the
|
|
154
|
+
// separator rule below reads the raw spelling.
|
|
155
|
+
const route = rawSegments.findIndex((s) => {
|
|
156
|
+
const decoded = safeDecode(s);
|
|
157
|
+
return decoded === 'workspace' || decoded === 'embed';
|
|
158
|
+
});
|
|
159
|
+
const rest = route >= 0 && rawSegments.length >= route + 3 ? rawSegments.slice(route + 2) : rawSegments;
|
|
160
|
+
refuseEncodedSeparators(rest.join('/'));
|
|
161
|
+
pathPart = rest.map((s) => safeDecode(s)).join('/');
|
|
162
|
+
} else {
|
|
163
|
+
const hashIndex = ref.indexOf('#');
|
|
164
|
+
fragment = hashIndex >= 0 ? safeDecode(ref.slice(hashIndex + 1)) : '';
|
|
165
|
+
const rawPath = hashIndex >= 0 ? ref.slice(0, hashIndex) : ref;
|
|
166
|
+
refuseEncodedSeparators(rawPath);
|
|
167
|
+
pathPart = rawPath.split('/').map((s) => safeDecode(s)).join('/');
|
|
168
|
+
}
|
|
169
|
+
|
|
170
|
+
let repoRelative = pathPart.replace(/^\.\//, '').replace(/^\/+/, '');
|
|
171
|
+
if (repoRelative.startsWith(`${kbDirName}/`)) {
|
|
172
|
+
repoRelative = repoRelative.slice(kbDirName.length + 1);
|
|
173
|
+
}
|
|
174
|
+
|
|
175
|
+
const slug = fragment.trim() || undefined;
|
|
176
|
+
|
|
177
|
+
if (looksLikeNodeId(repoRelative)) return { nodeId: repoRelative, slug };
|
|
178
|
+
if (isSafeRepoRelativeEmbedPath(repoRelative)) return { repoRelative, slug };
|
|
179
|
+
throw new EmbedRefParseError(`Not a safe knowledge-base path: ${pathPart}`);
|
|
180
|
+
}
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
/** The presented embed token is missing, malformed, or expired. */
|
|
2
|
+
export class EmbedTokenError extends Error {
|
|
3
|
+
constructor(message = 'Invalid or expired embed token') {
|
|
4
|
+
super(message);
|
|
5
|
+
this.name = 'EmbedTokenError';
|
|
6
|
+
}
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
/**
|
|
10
|
+
* The referenced file doesn't exist on the embed's target branch (→ 404).
|
|
11
|
+
* Raised at mint time for a dead reference and at load time when the file was
|
|
12
|
+
* renamed or removed after the token was minted. The message is user-facing —
|
|
13
|
+
* it is what the embedded view shows for the reference.
|
|
14
|
+
*/
|
|
15
|
+
export class EmbedNodeNotFoundError extends Error {
|
|
16
|
+
constructor(message: string) {
|
|
17
|
+
super(message);
|
|
18
|
+
this.name = 'EmbedNodeNotFoundError';
|
|
19
|
+
}
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
/** The viewer lacks the access the operation needs on the default branch. */
|
|
23
|
+
export class EmbedAccessError extends Error {
|
|
24
|
+
constructor(message = 'You do not have edit access to this file') {
|
|
25
|
+
super(message);
|
|
26
|
+
this.name = 'EmbedAccessError';
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
/**
|
|
31
|
+
* Another editor holds the file lock, so a save can't proceed (→ 409). Raised
|
|
32
|
+
* when the viewer's own lock lapsed — a frame left hidden past the TTL — and
|
|
33
|
+
* somebody else took the file in the meantime.
|
|
34
|
+
*/
|
|
35
|
+
export class EmbedLockedError extends Error {
|
|
36
|
+
constructor(
|
|
37
|
+
/** Display name / email of the current lock holder, for the UI. */
|
|
38
|
+
public readonly heldBy: string,
|
|
39
|
+
) {
|
|
40
|
+
super(`This file is currently being edited by ${heldBy}`);
|
|
41
|
+
this.name = 'EmbedLockedError';
|
|
42
|
+
}
|
|
43
|
+
}
|
|
@@ -0,0 +1,203 @@
|
|
|
1
|
+
import type { AuthUser } from '@bevel-software/platform-shared';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* WHO an embed token was minted for.
|
|
5
|
+
*
|
|
6
|
+
* Two kinds, and the difference is only how the identity is spelled:
|
|
7
|
+
*
|
|
8
|
+
* - `user` — a Hexis user id. What the MCP `open_page` tool mints: the MCP
|
|
9
|
+
* session already authenticated somebody (a signed-in user, or the owner
|
|
10
|
+
* of the connection key the agent carries), so the token names them
|
|
11
|
+
* outright and there is nothing to link.
|
|
12
|
+
* - `atlassian` — an outside account id, resolved to a Hexis user through
|
|
13
|
+
* the account-link table. What the Atlassian connector's mint produces,
|
|
14
|
+
* and the reason that table exists.
|
|
15
|
+
*
|
|
16
|
+
* Both resolve to one user, whose read and write access the view then obeys.
|
|
17
|
+
* Claims stay PSEUDONYMOUS whichever kind it is — a token travels as an
|
|
18
|
+
* iframe URL parameter, so it carries an id and never an address or a name.
|
|
19
|
+
*/
|
|
20
|
+
export type EmbedSubject =
|
|
21
|
+
| { kind: 'user'; userId: string }
|
|
22
|
+
| { kind: 'atlassian'; accountId: string };
|
|
23
|
+
|
|
24
|
+
/** Result of minting an embed token for one file. */
|
|
25
|
+
export interface EmbedTokenResult {
|
|
26
|
+
/** Signed, short-lived token scoping the bearer to one file + heading + identity. */
|
|
27
|
+
token: string;
|
|
28
|
+
/** Ready-to-iframe URL: `<frontend>/embed?token=…` (the SPA embed route). */
|
|
29
|
+
embedUrl: string;
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
/** How the embed should render a file: with the app's renderer for its type. */
|
|
33
|
+
export interface EmbedFileView {
|
|
34
|
+
/** Display name — file basename without its extension. */
|
|
35
|
+
nodeName: string;
|
|
36
|
+
/** Repo-relative path of the embedded file. */
|
|
37
|
+
repoRelative: string;
|
|
38
|
+
/** Workspace-relative path (`<kbDir>/<repoRelative>`) — what the app's renderers take. */
|
|
39
|
+
workspacePath: string;
|
|
40
|
+
/** The knowledge-base directory name, so the view can build app URLs. */
|
|
41
|
+
kbDirName: string;
|
|
42
|
+
/** The branch rendered. Always the deployment's default branch. */
|
|
43
|
+
branch: string;
|
|
44
|
+
/** The file's address in the app, absolute. */
|
|
45
|
+
appUrl: string;
|
|
46
|
+
/** Heading slug this embed is scoped to; absent for a whole file. */
|
|
47
|
+
heading?: string;
|
|
48
|
+
/**
|
|
49
|
+
* The file's TEXT, for a renderer that takes text (markdown, HTML source,
|
|
50
|
+
* plain text, CSV, a `.tool`). Empty for a file whose renderer fetches its
|
|
51
|
+
* own bytes — an image, a PDF, a Word document — which read them from
|
|
52
|
+
* `GET /api/embed/raw` under this same token.
|
|
53
|
+
*/
|
|
54
|
+
content: string;
|
|
55
|
+
/**
|
|
56
|
+
* Whether `content` carries the file's text at all. False says "this
|
|
57
|
+
* renderer reads bytes": the difference between an empty file and a
|
|
58
|
+
* picture, which the view must not confuse.
|
|
59
|
+
*/
|
|
60
|
+
contentIsText: boolean;
|
|
61
|
+
/** Whether the token's identity resolved to a Hexis user at all. */
|
|
62
|
+
linked: boolean;
|
|
63
|
+
/** Whether that user may READ this file. Always false when unlinked. */
|
|
64
|
+
canRead: boolean;
|
|
65
|
+
/** Whether that user may WRITE this file on the default branch. */
|
|
66
|
+
canWrite: boolean;
|
|
67
|
+
/** Where to send an unlinked viewer to link their account. */
|
|
68
|
+
linkUrl: string;
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
/** Outcome of an Edit-time lock acquisition. */
|
|
72
|
+
export interface EmbedLockResult {
|
|
73
|
+
acquired: boolean;
|
|
74
|
+
/** Current holder's display name when `acquired` is false. */
|
|
75
|
+
holderName?: string;
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
/** Where a proposal landed, so the view can point at it. */
|
|
79
|
+
export interface EmbedProposalResult {
|
|
80
|
+
/** The suggestions branch the proposal was committed to. */
|
|
81
|
+
branch: string;
|
|
82
|
+
/** The change request number, when one could be read back. */
|
|
83
|
+
number?: number;
|
|
84
|
+
/** The change request's address in the app, when its number is known. */
|
|
85
|
+
url?: string;
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
/** One outside account linked to a Hexis user (the Connected apps screen). */
|
|
89
|
+
export interface EmbedLinkedAccount {
|
|
90
|
+
atlassianAccountId: string;
|
|
91
|
+
/** Epoch ms of when the link was created. */
|
|
92
|
+
createdAt: number;
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
/**
|
|
96
|
+
* Resolve a bare node id (the copy-link form `/workspace/<branch>/<id>`) to
|
|
97
|
+
* its repo-relative path, or null when no node has that id.
|
|
98
|
+
*
|
|
99
|
+
* Core has no node graph, so core refuses an id reference. A deployment that
|
|
100
|
+
* does keeps the Atlassian connector's id references working by registering
|
|
101
|
+
* one of these — the mint's only extension point, and the reason the connector
|
|
102
|
+
* needs no change when the embed moves into Hexis.
|
|
103
|
+
*/
|
|
104
|
+
export type EmbedNodeIdResolver = (nodeId: string) => Promise<string | null>;
|
|
105
|
+
|
|
106
|
+
/**
|
|
107
|
+
* What the embed service needs of the workspace: the clone of a branch, and
|
|
108
|
+
* four verbs on one file of it. A port rather than the workspace service
|
|
109
|
+
* itself, so a deployment (or a test) hands in whatever answers these.
|
|
110
|
+
*/
|
|
111
|
+
export interface EmbedWorkspacePort {
|
|
112
|
+
getOrCreateForBranch(branch: string): Promise<{ id: string }>;
|
|
113
|
+
isFile(workspaceId: string, wsPath: string): Promise<boolean>;
|
|
114
|
+
readFileBinary(workspaceId: string, wsPath: string): Promise<Buffer>;
|
|
115
|
+
writeFile(workspaceId: string, wsPath: string, content: string): Promise<void>;
|
|
116
|
+
/** One mutation at a time per resolved path, in this process: `op` runs after every turn already taken for `wsPath`. */
|
|
117
|
+
withPathTurn<T>(workspaceId: string, wsPath: string, op: () => Promise<T>): Promise<T>;
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
/** What the embed service needs of authentication: a user by id, and the email-domain rule. */
|
|
121
|
+
export interface EmbedAuthPort {
|
|
122
|
+
getUserById(userId: string): Promise<AuthUser | null>;
|
|
123
|
+
isEmailDomainAllowed(email: string): boolean;
|
|
124
|
+
/** Whether the account is on: it exists and no admin switched it off — the gate every credential passes. */
|
|
125
|
+
isActive(userId: string): Promise<boolean>;
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
/**
|
|
129
|
+
* Mints and consumes embed tokens that let a host — an MCP App's sandbox, an
|
|
130
|
+
* Atlassian panel — display and edit one knowledge-base file inside itself.
|
|
131
|
+
*
|
|
132
|
+
* The file is the source of truth: editing acquires the platform's file lock,
|
|
133
|
+
* saving writes to the default branch and releases it (which commits), and a
|
|
134
|
+
* viewer who may not write proposes instead, exactly as the app's file page
|
|
135
|
+
* does. The framed data methods — load, raw bytes, lock, heartbeat, cancel,
|
|
136
|
+
* save, propose — authenticate by the TOKEN and nothing else: no session is
|
|
137
|
+
* consulted, and a request that carries one without a token is refused. The
|
|
138
|
+
* account-management methods (`linkAccount`, `listLinkedAccounts`,
|
|
139
|
+
* `unlinkAccount`) are the exception, called from session-authenticated
|
|
140
|
+
* routes on a page no host may frame.
|
|
141
|
+
*/
|
|
142
|
+
export interface IEmbedService {
|
|
143
|
+
/**
|
|
144
|
+
* Whether the SHARED-SECRET mint (`POST /api/embed/token`) is configured.
|
|
145
|
+
*
|
|
146
|
+
* Only that one route: the embed surface itself is part of every deployment
|
|
147
|
+
* now, because the MCP App is, and its mint authenticates by the MCP
|
|
148
|
+
* session rather than by a secret. A deployment with no
|
|
149
|
+
* `EMBED_SHARED_SECRET` simply has no Atlassian connector pointed at it.
|
|
150
|
+
*/
|
|
151
|
+
sharedSecretConfigured(): boolean;
|
|
152
|
+
/** Constant-time check of the connector→backend shared secret. */
|
|
153
|
+
verifySharedSecret(secret: string | undefined): boolean;
|
|
154
|
+
|
|
155
|
+
/** Mint for a Hexis user — the MCP path. `reference` is a path or an app URL. */
|
|
156
|
+
mintForUser(input: { userId: string; reference: string }): Promise<EmbedTokenResult>;
|
|
157
|
+
|
|
158
|
+
/**
|
|
159
|
+
* Mint for an outside account — the Atlassian connector's path, unchanged.
|
|
160
|
+
* `email` is consulted only by the allowed-email-domains gate and never
|
|
161
|
+
* enters the token.
|
|
162
|
+
*/
|
|
163
|
+
mintToken(input: { accountId: string; email?: string; reference: string }): Promise<EmbedTokenResult>;
|
|
164
|
+
|
|
165
|
+
/** Load the file the token is scoped to, with the viewer's read/write status. */
|
|
166
|
+
loadFile(token: string): Promise<EmbedFileView>;
|
|
167
|
+
|
|
168
|
+
/**
|
|
169
|
+
* The raw bytes of the embedded file, or of one asset `path` beside it (an
|
|
170
|
+
* image a markdown page shows — a file no reader edits as text, or an SVG,
|
|
171
|
+
* the one text format a page draws as a picture), for the app renderers
|
|
172
|
+
* that read bytes rather than the text buffer. Gated on the token
|
|
173
|
+
* identity's read access, per file. Any other text page than the embedded
|
|
174
|
+
* one is refused: the token scopes the view to ONE page, and another page
|
|
175
|
+
* opens in the app, never through this view's token.
|
|
176
|
+
*/
|
|
177
|
+
readBytes(token: string, path?: string): Promise<{ bytes: Buffer; path: string }>;
|
|
178
|
+
|
|
179
|
+
/** Acquire the edit lock (Edit clicked). Requires write access. */
|
|
180
|
+
acquireLock(token: string): Promise<EmbedLockResult>;
|
|
181
|
+
/** Keep a held lock alive while editing. */
|
|
182
|
+
heartbeat(token: string): Promise<void>;
|
|
183
|
+
/** Drop the lock without committing (Cancel / view closed). */
|
|
184
|
+
cancel(token: string): Promise<void>;
|
|
185
|
+
/** Write `content` to the default branch, then release the lock (commits). */
|
|
186
|
+
save(token: string, content: string): Promise<void>;
|
|
187
|
+
/**
|
|
188
|
+
* File `content` as a change request authored by the token's identity, on
|
|
189
|
+
* that person's own suggestions branch. What a viewer without write access
|
|
190
|
+
* does instead of saving; nothing lands on the default branch.
|
|
191
|
+
*/
|
|
192
|
+
propose(token: string, content: string): Promise<EmbedProposalResult>;
|
|
193
|
+
|
|
194
|
+
/** Link the token's outside account to `userId` (called after sign-in). */
|
|
195
|
+
linkAccount(token: string, userId: string): Promise<void>;
|
|
196
|
+
/** The outside accounts linked to `userId`, for the Connected apps screen. */
|
|
197
|
+
listLinkedAccounts(userId: string): Promise<EmbedLinkedAccount[]>;
|
|
198
|
+
/**
|
|
199
|
+
* Remove one of `userId`'s links (self-service disconnect / erasure).
|
|
200
|
+
* False when the account isn't linked to this user.
|
|
201
|
+
*/
|
|
202
|
+
unlinkAccount(userId: string, accountId: string): Promise<boolean>;
|
|
203
|
+
}
|