@weavecode/weave 0.1.7 → 0.1.9
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/node_modules/@modelcontextprotocol/sdk/node_modules/@hono/node-server/dist/index.cjs +31 -6
- package/node_modules/@modelcontextprotocol/sdk/node_modules/@hono/node-server/dist/index.mjs +31 -6
- package/node_modules/@modelcontextprotocol/sdk/node_modules/@hono/node-server/package.json +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/express-rate-limit/dist/index.cjs +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/express-rate-limit/dist/index.mjs +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/express-rate-limit/node_modules/ip-address/README.md +39 -39
- package/node_modules/@modelcontextprotocol/sdk/node_modules/express-rate-limit/node_modules/ip-address/dist/ipv6.js +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/express-rate-limit/node_modules/ip-address/package.json +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/express-rate-limit/package.json +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/adapter/bun/serve-static.js +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/adapter/bun/websocket.js +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/context.js +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/helper/css/common.js +3 -5
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/hono-base.js +4 -10
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/hono.js +0 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/middleware/basic-auth/index.js +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/middleware/bearer-auth/index.js +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/middleware/csrf/index.js +2 -2
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/middleware/jwk/jwk.js +2 -2
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/middleware/jwt/jwt.js +2 -2
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/middleware/mount/index.js +4 -4
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/router/reg-exp-router/node.js +13 -11
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/router/reg-exp-router/prepared-router.js +4 -4
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/router/reg-exp-router/router.js +39 -51
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/router/reg-exp-router/trie.js +15 -5
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/utils/jwt/jwt.js +2 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/utils/mount.js +35 -0
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/utils/url.js +10 -0
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/cjs/validator/validator.js +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/context.js +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/helper/css/common.js +3 -5
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/hono-base.js +4 -10
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/hono.js +0 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/middleware/basic-auth/index.js +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/middleware/bearer-auth/index.js +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/middleware/csrf/index.js +2 -2
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/middleware/jwk/jwk.js +2 -2
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/middleware/jwt/jwt.js +2 -2
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/middleware/language/language.js +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/middleware/mount/index.js +4 -4
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/router/reg-exp-router/node.js +13 -11
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/router/reg-exp-router/prepared-router.js +5 -5
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/router/reg-exp-router/router.js +40 -52
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/router/reg-exp-router/trie.js +15 -5
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/types/middleware/mount/index.d.ts +1 -0
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/types/router/reg-exp-router/node.d.ts +3 -3
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/types/router/reg-exp-router/trie.d.ts +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/types/utils/mount.d.ts +4 -0
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/types/utils/url.d.ts +1 -0
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/utils/jwt/jwt.js +2 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/utils/mount.js +34 -0
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/utils/url.js +10 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/dist/validator/validator.js +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/hono/package.json +1 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/jose/dist/webapi/jwks/remote.js +3 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/jose/dist/webapi/lib/deflate.js +2 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/jose/dist/webapi/lib/jwt_claims_set.js +2 -1
- package/node_modules/@modelcontextprotocol/sdk/node_modules/jose/package.json +1 -1
- package/node_modules/@weavecode/cli/dist/cli.js +4 -4
- package/node_modules/@weavecode/cli/dist/commands/chpass.js +1 -1
- package/node_modules/@weavecode/cli/dist/commands/daemon-auth.js +1 -1
- package/node_modules/@weavecode/cli/dist/commands/daemon.js +2 -2
- package/node_modules/@weavecode/cli/dist/commands/dashboard.js +2 -2
- package/node_modules/@weavecode/cli/dist/commands/doctor.js +1 -1
- package/node_modules/@weavecode/cli/dist/commands/init.js +1 -1
- package/node_modules/@weavecode/cli/dist/commands/scan.js +1 -1
- package/node_modules/@weavecode/cli/dist/commands/status.js +2 -2
- package/node_modules/@weavecode/cli/dist/commands/uninstall.js +1 -1
- package/node_modules/@weavecode/cli/dist/i18n/dict/en.js +3 -3
- package/node_modules/@weavecode/cli/dist/i18n/dict/zh.d.ts +7 -0
- package/node_modules/@weavecode/cli/dist/i18n/dict/zh.js +3 -3
- package/node_modules/@weavecode/cli/dist/i18n/index.js +1 -1
- package/node_modules/@weavecode/cli/dist/i18n/t.js +1 -1
- package/node_modules/@weavecode/cli/dist/init/claudemd-gen.js +5 -5
- package/node_modules/@weavecode/cli/dist/init/executor.js +3 -3
- package/node_modules/@weavecode/cli/dist/init/git-commit.js +2 -2
- package/node_modules/@weavecode/cli/dist/init/git-exclude.d.ts +20 -0
- package/node_modules/@weavecode/cli/dist/init/git-exclude.js +7 -0
- package/node_modules/@weavecode/cli/dist/init/harnesses/claude.js +7 -7
- package/node_modules/@weavecode/cli/dist/init/harnesses/codex.js +1 -1
- package/node_modules/@weavecode/cli/dist/init/instruction-files.d.ts +14 -0
- package/node_modules/@weavecode/cli/dist/init/instruction-files.js +1 -0
- package/node_modules/@weavecode/cli/dist/init/instruction-link.js +1 -1
- package/node_modules/@weavecode/cli/dist/init/plugin-templates.js +1 -1
- package/node_modules/@weavecode/cli/dist/init/prompt.js +4 -4
- package/node_modules/@weavecode/cli/dist/init/provision.js +1 -1
- package/node_modules/@weavecode/cli/dist/init/uninstall.js +6 -6
- package/node_modules/@weavecode/cli/dist/init/wiring.js +1 -1
- package/node_modules/@weavecode/cli/dist/parser.js +1 -1
- package/node_modules/@weavecode/cli/dist/statusline/ansi.js +1 -1
- package/node_modules/@weavecode/cli/package.json +5 -5
- package/node_modules/@weavecode/core/dist/harness-checks.js +1 -1
- package/node_modules/@weavecode/core/dist/harness.d.ts +115 -0
- package/node_modules/@weavecode/core/dist/harness.js +1 -1
- package/node_modules/@weavecode/core/dist/index.d.ts +1 -1
- package/node_modules/@weavecode/core/dist/index.js +1 -1
- package/node_modules/@weavecode/core/dist/platform.js +1 -1
- package/node_modules/@weavecode/core/dist/types.d.ts +4 -4
- package/node_modules/@weavecode/core/dist/types.js +1 -1
- package/node_modules/@weavecode/core/dist/utils/fs.js +1 -1
- package/node_modules/@weavecode/core/package.json +1 -1
- package/node_modules/@weavecode/harness/dist/claude/assets.js +3 -3
- package/node_modules/@weavecode/harness/dist/claude/capture.js +9 -9
- package/node_modules/@weavecode/harness/dist/claude/commands.d.ts +2 -0
- package/node_modules/@weavecode/harness/dist/claude/commands.js +3 -2
- package/node_modules/@weavecode/harness/dist/claude/config.js +2 -2
- package/node_modules/@weavecode/harness/dist/claude/detect.js +1 -1
- package/node_modules/@weavecode/harness/dist/claude/edits.js +1 -1
- package/node_modules/@weavecode/harness/dist/claude/event-source.js +1 -1
- package/node_modules/@weavecode/harness/dist/claude/images.js +2 -2
- package/node_modules/@weavecode/harness/dist/claude/index.js +1 -1
- package/node_modules/@weavecode/harness/dist/claude/liveness.js +1 -1
- package/node_modules/@weavecode/harness/dist/claude/mcp-gen.js +1 -1
- package/node_modules/@weavecode/harness/dist/claude/messaging.js +2 -2
- package/node_modules/@weavecode/harness/dist/claude/model-aliases.js +1 -1
- package/node_modules/@weavecode/harness/dist/claude/narration.js +1 -1
- package/node_modules/@weavecode/harness/dist/claude/peers.js +1 -1
- package/node_modules/@weavecode/harness/dist/claude/plan.js +1 -1
- package/node_modules/@weavecode/harness/dist/claude/plugins.js +4 -4
- package/node_modules/@weavecode/harness/dist/claude/prompt-inbox.js +1 -1
- package/node_modules/@weavecode/harness/dist/claude/prompt.js +3 -3
- package/node_modules/@weavecode/harness/dist/claude/questions.js +2 -2
- package/node_modules/@weavecode/harness/dist/claude/resume.js +1 -1
- package/node_modules/@weavecode/harness/dist/claude/rewind.js +1 -1
- package/node_modules/@weavecode/harness/dist/claude/settings-gen.js +1 -1
- package/node_modules/@weavecode/harness/dist/claude/side-question.js +2 -2
- package/node_modules/@weavecode/harness/dist/claude/statusline/generator.d.ts +6 -0
- package/node_modules/@weavecode/harness/dist/claude/statusline/generator.js +21 -14
- package/node_modules/@weavecode/harness/dist/claude/statusline/git-cache.js +1 -1
- package/node_modules/@weavecode/harness/dist/claude/statusline/surface.js +2 -2
- package/node_modules/@weavecode/harness/dist/claude/transcript-cursor.js +2 -2
- package/node_modules/@weavecode/harness/dist/claude/transcript.js +7 -7
- package/node_modules/@weavecode/harness/dist/codex/assets.js +1 -1
- package/node_modules/@weavecode/harness/dist/codex/capture.js +2 -2
- package/node_modules/@weavecode/harness/dist/codex/commands.js +4 -4
- package/node_modules/@weavecode/harness/dist/codex/config.js +2 -2
- package/node_modules/@weavecode/harness/dist/codex/detect.js +1 -1
- package/node_modules/@weavecode/harness/dist/codex/event-source.js +2 -2
- package/node_modules/@weavecode/harness/dist/codex/images.js +1 -1
- package/node_modules/@weavecode/harness/dist/codex/index.js +1 -1
- package/node_modules/@weavecode/harness/dist/codex/liveness.js +1 -1
- package/node_modules/@weavecode/harness/dist/codex/mcp.js +1 -1
- package/node_modules/@weavecode/harness/dist/codex/messaging.js +2 -2
- package/node_modules/@weavecode/harness/dist/codex/narration.js +1 -1
- package/node_modules/@weavecode/harness/dist/codex/plugin-state.js +1 -1
- package/node_modules/@weavecode/harness/dist/codex/plugins.js +3 -3
- package/node_modules/@weavecode/harness/dist/codex/provision.js +1 -1
- package/node_modules/@weavecode/harness/dist/codex/questions.js +2 -2
- package/node_modules/@weavecode/harness/dist/codex/rollout.js +5 -5
- package/node_modules/@weavecode/harness/dist/codex/side-question.js +4 -4
- package/node_modules/@weavecode/harness/dist/codex/titles.js +4 -4
- package/node_modules/@weavecode/harness/dist/codex/toml.js +13 -13
- package/node_modules/@weavecode/harness/dist/codex/transcript.js +2 -2
- package/node_modules/@weavecode/harness/dist/driver.d.ts +6 -0
- package/node_modules/@weavecode/harness/dist/driver.js +1 -1
- package/node_modules/@weavecode/harness/dist/init/generated.js +2 -2
- package/node_modules/@weavecode/harness/dist/init/pipeline.js +1 -1
- package/node_modules/@weavecode/harness/dist/registry-wiring.js +1 -1
- package/node_modules/@weavecode/harness/dist/shared/install-link.js +1 -1
- package/node_modules/@weavecode/harness/dist/shared/json-cap.js +1 -1
- package/node_modules/@weavecode/harness/package.json +2 -2
- package/node_modules/@weavecode/server/dist/config/dotted.js +1 -1
- package/node_modules/@weavecode/server/dist/config/profiles.js +2 -2
- package/node_modules/@weavecode/server/dist/daemon/ai-config.js +2 -2
- package/node_modules/@weavecode/server/dist/daemon/ai-context.js +6 -6
- package/node_modules/@weavecode/server/dist/daemon/ai-routes.js +4 -4
- package/node_modules/@weavecode/server/dist/daemon/api-log.js +3 -3
- package/node_modules/@weavecode/server/dist/daemon/auth-routes.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/auto-start.js +3 -3
- package/node_modules/@weavecode/server/dist/daemon/capture-routes.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/config-routes.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/cron.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/dashboard-auth.js +2 -2
- package/node_modules/@weavecode/server/dist/daemon/dashboard-pusher.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/decision-config.js +2 -2
- package/node_modules/@weavecode/server/dist/daemon/dev-entry.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/entry.js +2 -2
- package/node_modules/@weavecode/server/dist/daemon/fs-browser.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/hook-pipeline.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/hooks-routes.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/http.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/liveness.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/mcp-orchestration.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/narration-watcher.js +2 -2
- package/node_modules/@weavecode/server/dist/daemon/opener/backend-ghostty.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/opener/backend-iterm.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/opener/backend-konsole.js +2 -2
- package/node_modules/@weavecode/server/dist/daemon/opener/backend-terminal-app.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/opener/backend-wezterm.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/opener/backend-wt.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/opener/backend.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/opener/pty-terminals.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/opener/shared.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/opener/wezterm-mux.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/opener/wt.js +3 -3
- package/node_modules/@weavecode/server/dist/daemon/opener.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/pet-seed.d.ts +4 -0
- package/node_modules/@weavecode/server/dist/daemon/pet-seed.js +2 -0
- package/node_modules/@weavecode/server/dist/daemon/pet-window.d.ts +17 -0
- package/node_modules/@weavecode/server/dist/daemon/pet-window.js +2 -0
- package/node_modules/@weavecode/server/dist/daemon/port.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/project-files.d.ts +1 -1
- package/node_modules/@weavecode/server/dist/daemon/project-files.js +2 -2
- package/node_modules/@weavecode/server/dist/daemon/project-harnesses.js +2 -2
- package/node_modules/@weavecode/server/dist/daemon/project-updates-refresher.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/prompt-images.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/routes/hooks-admin.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/routes/installations.d.ts +29 -0
- package/node_modules/@weavecode/server/dist/daemon/routes/installations.js +1 -0
- package/node_modules/@weavecode/server/dist/daemon/routes/market.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/routes/orchestration.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/routes/path-refs.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/routes/pets.d.ts +3 -0
- package/node_modules/@weavecode/server/dist/daemon/routes/pets.js +1 -0
- package/node_modules/@weavecode/server/dist/daemon/routes/project-files.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/routes/projects.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/routes/search.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/routes/session-control.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/routes/session-insights.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/routes/settings-statusline.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/routes/uploads.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/routes/visualizations.js +2 -1
- package/node_modules/@weavecode/server/dist/daemon/routes/watches.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/server.d.ts +4 -0
- package/node_modules/@weavecode/server/dist/daemon/server.js +8 -8
- package/node_modules/@weavecode/server/dist/daemon/session-open.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/session-probe.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/settings.d.ts +21 -0
- package/node_modules/@weavecode/server/dist/daemon/settings.js +2 -2
- package/node_modules/@weavecode/server/dist/daemon/snapshot-refresher.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/sse-hub.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/start.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/state.js +2 -2
- package/node_modules/@weavecode/server/dist/daemon/static.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/terminal-topology-refresher.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/tls.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/toolkit-routes.js +1 -1
- package/node_modules/@weavecode/server/dist/daemon/upload-sessions.js +1 -1
- package/node_modules/@weavecode/server/dist/db/db.d.ts +4 -1
- package/node_modules/@weavecode/server/dist/db/db.js +2 -2
- package/node_modules/@weavecode/server/dist/db/layout.d.ts +5 -0
- package/node_modules/@weavecode/server/dist/db/layout.js +2 -1
- package/node_modules/@weavecode/server/dist/db/paths.d.ts +9 -0
- package/node_modules/@weavecode/server/dist/db/paths.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/answer-keys.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/dashboard-rate.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/decision-judge.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/delivery/ack-gate.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/delivery/channels.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/delivery/keys.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/delivery/queue.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/delivery/relay.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/delivery/send.js +2 -2
- package/node_modules/@weavecode/server/dist/hooks/delivery/views.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/dispatcher.js +6 -6
- package/node_modules/@weavecode/server/dist/hooks/edge-extract.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/handlers/webhook.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/headless-runner.js +2 -2
- package/node_modules/@weavecode/server/dist/hooks/inbox-socket.js +2 -2
- package/node_modules/@weavecode/server/dist/hooks/inbox-worker.js +3 -3
- package/node_modules/@weavecode/server/dist/hooks/match.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/message-deliverer.js +5 -5
- package/node_modules/@weavecode/server/dist/hooks/mirror.js +4 -4
- package/node_modules/@weavecode/server/dist/hooks/orchestration-engine.js +7 -7
- package/node_modules/@weavecode/server/dist/hooks/orchestration-graph.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/plugin-installer.js +3 -3
- package/node_modules/@weavecode/server/dist/hooks/plugin-loader.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/plugin-project-state.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/prompt-flusher.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/promptbox.js +8 -8
- package/node_modules/@weavecode/server/dist/hooks/push-notify.js +2 -2
- package/node_modules/@weavecode/server/dist/hooks/question-tracker.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/registry.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/resume-runner.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/session-purge.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/side-questions.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/synthetic-sessions.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/toolkit-scan.js +1 -1
- package/node_modules/@weavecode/server/dist/hooks/toolkit.js +5 -5
- package/node_modules/@weavecode/server/dist/hooks/watch-engine.js +1 -1
- package/node_modules/@weavecode/server/dist/index.d.ts +1 -1
- package/node_modules/@weavecode/server/dist/index.js +1 -1
- package/node_modules/@weavecode/server/dist/install/apply-update.js +1 -1
- package/node_modules/@weavecode/server/dist/install/capabilities.js +1 -1
- package/node_modules/@weavecode/server/dist/install/codex-toml.js +1 -1
- package/node_modules/@weavecode/server/dist/install/file-assets.js +1 -1
- package/node_modules/@weavecode/server/dist/install/fingerprint.js +1 -1
- package/node_modules/@weavecode/server/dist/install/global-config.js +1 -1
- package/node_modules/@weavecode/server/dist/install/global-file-assets.js +1 -1
- package/node_modules/@weavecode/server/dist/install/init-files.d.ts +0 -9
- package/node_modules/@weavecode/server/dist/install/init-files.js +2 -2
- package/node_modules/@weavecode/server/dist/install/install-ledger.js +1 -1
- package/node_modules/@weavecode/server/dist/install/installer.js +1 -1
- package/node_modules/@weavecode/server/dist/install/library-index.js +1 -1
- package/node_modules/@weavecode/server/dist/install/mcp-rows.js +1 -1
- package/node_modules/@weavecode/server/dist/install/plugin-install.js +1 -1
- package/node_modules/@weavecode/server/dist/install/plugin-rows.js +1 -1
- package/node_modules/@weavecode/server/dist/install/plugin-templates.js +1 -1
- package/node_modules/@weavecode/server/dist/install/project-config.js +1 -1
- package/node_modules/@weavecode/server/dist/install/reader.js +1 -1
- package/node_modules/@weavecode/server/dist/install/scan-cache.js +1 -1
- package/node_modules/@weavecode/server/dist/install/scanner.js +1 -1
- package/node_modules/@weavecode/server/dist/install/settings-mcp.js +2 -2
- package/node_modules/@weavecode/server/dist/install/updates.js +1 -1
- package/node_modules/@weavecode/server/dist/market/builtin.js +1 -1
- package/node_modules/@weavecode/server/dist/market/identity.js +1 -1
- package/node_modules/@weavecode/server/dist/market/import.js +2 -2
- package/node_modules/@weavecode/server/dist/market/refresh.js +1 -1
- package/node_modules/@weavecode/server/dist/market/resolve.js +1 -1
- package/node_modules/@weavecode/server/dist/market/updates.js +1 -1
- package/node_modules/@weavecode/server/dist/registry.js +2 -2
- package/node_modules/@weavecode/server/dist/repositories/hook-dispatches.js +4 -4
- package/node_modules/@weavecode/server/dist/repositories/hook-events.d.ts +6 -0
- package/node_modules/@weavecode/server/dist/repositories/hook-events.js +8 -5
- package/node_modules/@weavecode/server/dist/repositories/hook-rules.js +4 -4
- package/node_modules/@weavecode/server/dist/repositories/libraries.js +1 -1
- package/node_modules/@weavecode/server/dist/repositories/orchestrations.js +7 -7
- package/node_modules/@weavecode/server/dist/repositories/plugin-states.js +1 -1
- package/node_modules/@weavecode/server/dist/repositories/projects.js +1 -1
- package/node_modules/@weavecode/server/dist/repositories/push-subscriptions.js +2 -2
- package/node_modules/@weavecode/server/dist/repositories/session-watches.js +4 -4
- package/node_modules/@weavecode/server/dist/repositories/sessions.js +2 -2
- package/node_modules/@weavecode/server/dist/repositories/uploads.js +11 -11
- package/node_modules/@weavecode/server/dist/statusline/cache-sweeper.js +1 -1
- package/node_modules/@weavecode/server/dist/statusline/generator.js +1 -1
- package/node_modules/@weavecode/server/dist/statusline/manager.js +3 -3
- package/node_modules/@weavecode/server/dist/surfaces.js +1 -1
- package/node_modules/@weavecode/server/dist/watch/cache.js +1 -1
- package/node_modules/@weavecode/server/dist/watch/classifier.js +1 -1
- package/node_modules/@weavecode/server/dist/watch/plugin-mods.js +1 -1
- package/node_modules/@weavecode/server/dist/watch/sync-scheduler.js +1 -1
- package/node_modules/@weavecode/server/dist/watch/watch-service.js +1 -1
- package/node_modules/@weavecode/server/package.json +4 -4
- package/node_modules/@weavecode/server/web/dist/assets/abnfDiagram-WEYOIA3C-S1lL1V_n.js +1 -0
- package/node_modules/@weavecode/server/web/dist/assets/{arc-CRZTRyjb.js → arc-CoTNHyHV.js} +1 -1
- package/node_modules/@weavecode/server/web/dist/assets/architectureDiagram-ZHVYKT53-C6ttfnzW.js +36 -0
- package/node_modules/@weavecode/server/web/dist/assets/{blockDiagram-RJAE7QA3-BIH8mSIZ.js → blockDiagram-RJAE7QA3-CYr3Cpu9.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/{c4Diagram-XDPPPE54-5YoKWFOD.js → c4Diagram-XDPPPE54-BFS7PhLD.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/channel-DxQHp3Yc.js +1 -0
- package/node_modules/@weavecode/server/web/dist/assets/{chunk-2E7WHVMD-B653kMXt.js → chunk-2E7WHVMD-DJ7X_Shu.js} +1 -1
- package/node_modules/@weavecode/server/web/dist/assets/{chunk-2Q5K7J3B-f_A4_eDz.js → chunk-2Q5K7J3B-B8nr2rdz.js} +1 -1
- package/node_modules/@weavecode/server/web/dist/assets/{chunk-4EMNKR2T-v5j5qNGj.js → chunk-4EMNKR2T-DmnZmUMU.js} +1 -1
- package/node_modules/@weavecode/server/web/dist/assets/chunk-55XCU76K-Xz9a8dmp.js +1 -0
- package/node_modules/@weavecode/server/web/dist/assets/{chunk-5VM5RSS4-BeROhLXN.js → chunk-5VM5RSS4-Dg9mg7pf.js} +1 -1
- package/node_modules/@weavecode/server/web/dist/assets/{chunk-JWPE2WC7-D6dXb_jr.js → chunk-JWPE2WC7-CmjTZO8o.js} +1 -1
- package/node_modules/@weavecode/server/web/dist/assets/{chunk-VQ5W62QI-CnHdSEMi.js → chunk-VQ5W62QI-D3YDdJ3E.js} +1 -1
- package/node_modules/@weavecode/server/web/dist/assets/chunk-XXDRQBXY-s1OG9sqW.js +1 -0
- package/node_modules/@weavecode/server/web/dist/assets/chunk-ZCHMQSOR-C3hINQU3.js +2 -0
- package/node_modules/@weavecode/server/web/dist/assets/{classDiagram-v2-4MYWR3UA-DQe1b_k8.js → classDiagram-v2-4MYWR3UA-BTsbYrVl.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/cose-bilkent-JH36ORCC-C0W8Y-jI.js +1 -0
- package/node_modules/@weavecode/server/web/dist/assets/{cynefin-EF2NZ3EQ-OZotFKUu.js → cynefin-EF2NZ3EQ-stAu4Rh-.js} +1 -1
- package/node_modules/@weavecode/server/web/dist/assets/cynefinDiagram-WF24UDRP-CqYibiiv.js +62 -0
- package/node_modules/@weavecode/server/web/dist/assets/dagre-NK4GIZVX-qqcoJAqB.js +4 -0
- package/node_modules/@weavecode/server/web/dist/assets/diagram-CBK3MWTC-D0YTopb7.js +24 -0
- package/node_modules/@weavecode/server/web/dist/assets/diagram-I5XIIV2D-Csvw6aYr.js +24 -0
- package/node_modules/@weavecode/server/web/dist/assets/{diagram-ODIL2UCW-D9A6W8oB.js → diagram-ODIL2UCW-Dl0tYLkF.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/{diagram-PFBEJUXE-PeI-eyu2.js → diagram-PFBEJUXE-BCPSWZPe.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/diagram-RJA3I4VV-ETg-BrAJ.js +41 -0
- package/node_modules/@weavecode/server/web/dist/assets/{diagram-TYUNFSNR-D5KieEw5.js → diagram-TYUNFSNR-_M6ZxBG7.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/ebnfDiagram-V4P3TTPT-C-e_W7qx.js +1 -0
- package/node_modules/@weavecode/server/web/dist/assets/{elk-QONTBCTQ-D3xrVg0U.js → elk-QONTBCTQ-B5TBharB.js} +3 -3
- package/node_modules/@weavecode/server/web/dist/assets/{erDiagram-KYQIGQAA-y_V1cor7.js → erDiagram-KYQIGQAA-D08rj2pv.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/{flowDiagram-IUGLLWBU-BJ8Z0MkF.js → flowDiagram-IUGLLWBU-BALTxsKh.js} +1 -1
- package/node_modules/@weavecode/server/web/dist/assets/ganttDiagram-R7GPNTJY-Cts193jT.js +292 -0
- package/node_modules/@weavecode/server/web/dist/assets/gitGraphDiagram-PDYL7XHY-L9qYUX0v.js +106 -0
- package/node_modules/@weavecode/server/web/dist/assets/infoDiagram-MVDRKAX5-Bv47rgU0.js +2 -0
- package/node_modules/@weavecode/server/web/dist/assets/{ishikawaDiagram-HPEHV2GE-ChEnND76.js → ishikawaDiagram-HPEHV2GE-Da8_s6cs.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/{journeyDiagram-BOSHW7O7-DHcNtpYF.js → journeyDiagram-BOSHW7O7-Bj3CjZOf.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/{kanban-definition-FNSA4HC5-Dft7qpW5.js → kanban-definition-FNSA4HC5-D1hicmMu.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/linear-CWQg2iA1.js +1 -0
- package/node_modules/@weavecode/server/web/dist/assets/main-XLn3EZFh.css +11 -0
- package/node_modules/@weavecode/server/web/dist/assets/main-bsb0lQoL.js +1096 -0
- package/node_modules/@weavecode/server/web/dist/assets/{mermaid.core-D_Dp_Kl2.js → mermaid.core-C-wP0Zg2.js} +4 -4
- package/node_modules/@weavecode/server/web/dist/assets/{mindmap-definition-6OY57UG3-CM6OAd_-.js → mindmap-definition-6OY57UG3-Dk0VKqre.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/modulepreload-polyfill-B5Qt9EMX.js +1 -0
- package/node_modules/@weavecode/server/web/dist/assets/pegDiagram-ECIUJNBX-Bp1K_F9z.js +1 -0
- package/node_modules/@weavecode/server/web/dist/assets/pet-J6izA90s.js +1 -0
- package/node_modules/@weavecode/server/web/dist/assets/pieDiagram-GNMPY74T-BZ4rGy3t.js +39 -0
- package/node_modules/@weavecode/server/web/dist/assets/{quadrantDiagram-D57K4MC3-D8pQ_PU2.js → quadrantDiagram-D57K4MC3-B4N5KRsR.js} +4 -4
- package/node_modules/@weavecode/server/web/dist/assets/railroadDiagram-Y72NRBL7-C8nx8oHf.js +1 -0
- package/node_modules/@weavecode/server/web/dist/assets/{requirementDiagram-EQYSW5RA-C90DU5Ny.js → requirementDiagram-EQYSW5RA-VSH57d0d.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/{sankeyDiagram-SY24JHO5-B_poYGgJ.js → sankeyDiagram-SY24JHO5-jUb1hcya.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/{sequenceDiagram-BLEHNHQU-DDW7b2Dn.js → sequenceDiagram-BLEHNHQU-E2BioCNi.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/sizeCapture-INFHLROL-BdKrbRmI.js +1 -0
- package/node_modules/@weavecode/server/web/dist/assets/{stateDiagram-v2-A6IESKWZ-CkVMAyxG.js → stateDiagram-v2-A6IESKWZ-tFz7uNM7.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/swimlanes-B3ENRKFQ-B9BAPDWw.js +1 -0
- package/node_modules/@weavecode/server/web/dist/assets/swimlanesDiagram-AYQRV4AK-DQ2NPLl9.js +8 -0
- package/node_modules/@weavecode/server/web/dist/assets/{timeline-definition-JXYKGLGB-DnhkRGLb.js → timeline-definition-JXYKGLGB-CofNnFTK.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/{usecaseDiagram-WPOLBNNX-_TdIjC6Z.js → usecaseDiagram-WPOLBNNX-DOvjhJjJ.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/{vennDiagram-Q3Y3IDCW-FzgsymXB.js → vennDiagram-Q3Y3IDCW-BcFHWnhS.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/{wardleyDiagram-IVAIDKWA-BwqimStC.js → wardleyDiagram-IVAIDKWA-Bz2aqRAs.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/assets/{xychartDiagram-4URNHDU4-CFjjVPIV.js → xychartDiagram-4URNHDU4-DpNF6Vsq.js} +2 -2
- package/node_modules/@weavecode/server/web/dist/index.html +3 -2
- package/node_modules/@weavecode/server/web/dist/pet.html +130 -0
- package/node_modules/@weavecode/templates/dist/index.d.ts +2 -0
- package/node_modules/@weavecode/templates/dist/index.js +1 -1
- package/node_modules/@weavecode/templates/dist/resources/pets/weave-spider/pet.json +7 -0
- package/node_modules/@weavecode/templates/dist/resources/pets/weave-spider/spritesheet.png +0 -0
- package/node_modules/@weavecode/templates/dist/resources/weave-market/.claude-plugin/marketplace.json +6 -0
- package/node_modules/@weavecode/templates/dist/resources/weave-market/plugins/core-skills/weave-pet-hatcher/.claude-plugin/plugin.json +8 -0
- package/node_modules/@weavecode/templates/dist/resources/weave-market/plugins/core-skills/weave-pet-hatcher/skills/weave-pet-hatcher/SKILL.md +121 -0
- package/node_modules/@weavecode/templates/dist/resources/weave-market/plugins/core-skills/weave-pet-hatcher/skills/weave-pet-hatcher/scripts/assemble-pet.mjs +308 -0
- package/node_modules/@weavecode/templates/dist/resources/weave-market/plugins/core-skills/weave-pet-hatcher/weave.json +4 -0
- package/node_modules/@weavecode/templates/package.json +2 -2
- package/package.json +11 -7
- package/scripts/preinstall.mjs +108 -0
- package/node_modules/@weavecode/server/web/dist/assets/abnfDiagram-WEYOIA3C-DDeQkTf5.js +0 -1
- package/node_modules/@weavecode/server/web/dist/assets/architectureDiagram-ZHVYKT53-Dj54DE3O.js +0 -36
- package/node_modules/@weavecode/server/web/dist/assets/channel-5VM93AJ8.js +0 -1
- package/node_modules/@weavecode/server/web/dist/assets/chunk-55XCU76K-CgEqeP7j.js +0 -1
- package/node_modules/@weavecode/server/web/dist/assets/chunk-XXDRQBXY-BkG_e6PE.js +0 -1
- package/node_modules/@weavecode/server/web/dist/assets/chunk-ZCHMQSOR-DxR-fxzs.js +0 -2
- package/node_modules/@weavecode/server/web/dist/assets/cose-bilkent-JH36ORCC-DThrA8S5.js +0 -1
- package/node_modules/@weavecode/server/web/dist/assets/cynefinDiagram-WF24UDRP-DJjq2hfT.js +0 -62
- package/node_modules/@weavecode/server/web/dist/assets/dagre-NK4GIZVX-C2vH93HT.js +0 -4
- package/node_modules/@weavecode/server/web/dist/assets/diagram-CBK3MWTC-DrF_ScM-.js +0 -24
- package/node_modules/@weavecode/server/web/dist/assets/diagram-I5XIIV2D-D1qoUJ4t.js +0 -24
- package/node_modules/@weavecode/server/web/dist/assets/diagram-RJA3I4VV-DITY0Rd8.js +0 -41
- package/node_modules/@weavecode/server/web/dist/assets/ebnfDiagram-V4P3TTPT-DDylK-gz.js +0 -1
- package/node_modules/@weavecode/server/web/dist/assets/ganttDiagram-R7GPNTJY-C0q-CS1T.js +0 -292
- package/node_modules/@weavecode/server/web/dist/assets/gitGraphDiagram-PDYL7XHY-BYTComiB.js +0 -106
- package/node_modules/@weavecode/server/web/dist/assets/index-BKxAxaVG.js +0 -1091
- package/node_modules/@weavecode/server/web/dist/assets/index-C0Sd4MH7.css +0 -11
- package/node_modules/@weavecode/server/web/dist/assets/infoDiagram-MVDRKAX5-DtixgjLP.js +0 -2
- package/node_modules/@weavecode/server/web/dist/assets/linear-DEo11t-X.js +0 -1
- package/node_modules/@weavecode/server/web/dist/assets/pegDiagram-ECIUJNBX-_QkY0h8Q.js +0 -1
- package/node_modules/@weavecode/server/web/dist/assets/pieDiagram-GNMPY74T-ZGr5vtDj.js +0 -39
- package/node_modules/@weavecode/server/web/dist/assets/railroadDiagram-Y72NRBL7-DUIo-WmA.js +0 -1
- package/node_modules/@weavecode/server/web/dist/assets/sizeCapture-INFHLROL-CmKoqX6K.js +0 -1
- package/node_modules/@weavecode/server/web/dist/assets/swimlanes-B3ENRKFQ-Dm_Omzky.js +0 -1
- package/node_modules/@weavecode/server/web/dist/assets/swimlanesDiagram-AYQRV4AK-Bjj8ZA4d.js +0 -8
|
@@ -1 +1 @@
|
|
|
1
|
-
import{homedir as j}from"node:os";import X from"node:path";import{checkHarness as Y,isHarness as A}from"@weavecode/core";import{readBody as g,sendJson as e}from"../http.js";import{FingerprintCache as z}from"../../install/fingerprint.js";import{installSkill as Z,uninstallSkill as q,installFileAsset as tt,uninstallFileAsset as rt,InstallConflictError as x,AssetNotFoundError as M}from"../../install/installer.js";import{isFileAssetCategory as K}from"../../install/file-assets.js";import{installGlobalSkill as et,uninstallGlobalSkill as at,readGlobalSkillGroups as it,resolveGlobalSkillDir as H,listGlobalSkillFiles as ot,readGlobalSkillFile as nt,ClaudeJsonCorruptError as ct}from"../../install/global-config.js";import{CodexTomlCorruptError as lt}from"../../install/codex-toml.js";import{forgetInstalled as st,recordInstalled as ut}from"../../install/install-ledger.js";import{readProjectFile as mt,readGlobalFile as ft,PathEscapeError as dt,FileTooLargeError as pt}from"../../install/reader.js";import{readMcpRows as gt}from"../../install/mcp-rows.js";import{setMcpEnableOverride as ht}from"../../install/settings-mcp.js";import{applyUpdate as bt,syncAll as yt}from"../../install/apply-update.js";import{buildLibraryIndex as kt}from"../../install/library-index.js";import{detectUpdates as wt}from"../../install/updates.js";import{detectPluginTemplateUpdates as St}from"../../install/plugin-templates.js";import{detectInitFileUpdates as jt,needsInit as vt}from"../../install/init-files.js";import{getLibraryScan as _,invalidateScan as b}from"../../install/scan-cache.js";import{installCapabilities as It}from"../../install/capabilities.js";import{BUILTIN_MCP_SERVERS as Pt}from"../../install/builtin-mcp.js";import{readPluginRows as Mt}from"../../install/plugin-rows.js";import{installPluginPack as Et}from"../../install/plugin-install.js";import{importFromDir as Nt,importFromGit as Ot,importLibraryIntoMarket as Tt}from"../../market/import.js";import{marketDir as E,readManifest as Ct}from"../../market/manifest.js";import{marketIdOf as $t}from"../../market/identity.js";import{isInsideDir as N,toRelPosix as Bt}from"../../market/resolve.js";import{checkMarketUpdates as Ft}from"../../market/updates.js";import{refreshMarketItems as Jt}from"../../market/refresh.js";import{ensureBuiltinMarket as Gt,isBuiltinMarketDir as S}from"../../market/builtin.js";import{removeInstalled as Lt}from"../../market/install-link.js";import{syncPlugins as Rt}from"../../hooks/plugin-project-state.js";import{assetSurfaces as Dt,pluginStateSurfaces as Ut,pluginSurfaces as W,pluginSurfaceFor as V}from"../../surfaces.js";function Q(o){return o.scope==="user"||o.category==="plugin"?!1:o.category==="mcp"?!!v(o.agent)?.mcpScopes().includes("project"):!0}function v(o){const r=o??"claude";return Dt().find(i=>i.harness===r)}function I(o,r){r instanceof x?o.statusCode=409:r instanceof M?o.statusCode=404:r instanceof ct||r instanceof lt?o.statusCode=500:o.statusCode=400,o.setHeader("content-type","application/json"),o.end(JSON.stringify({error:r instanceof Error?r.message:"Install failed"}))}function O(o,r){r instanceof dt?o.statusCode=403:r instanceof pt?o.statusCode=413:r instanceof M?o.statusCode=404:o.statusCode=400,o.setHeader("content-type","application/json"),o.end(JSON.stringify({error:r instanceof Error?r.message:"Read failed"}))}async function P(o,r){const i=N(o.path,E(r)),u=i?await Ct(o.path):null,d=S(o.path,r);return{id:o.id,kind:o.kind,addedAt:o.addedAt,path:o.path,relPath:N(o.path,r)?Bt(o.path,r):null,resourceId:i?X.basename(o.path):null,managed:i,builtin:d,namespace:i?$t(o.path,E(r)):void 0,legacy:!u&&!d,source:d?"builtin":u?.source??"legacy",origin:u?.origin??null,importedAt:u?.importedAt??null,commit:u?.commit??null,tags:await xt(o.path)}}const At={command:"command",agent:"agent",workflow:"workflow",rule:"rules","output-style":"output-style"};async function zt(o){const{plugins:r,skills:i,mcp:u,files:d}=await _(o),w={},h=(p,y)=>{y>0&&(w[p]=(w[p]??0)+y)};h("skill",i.length),h("mcp",u.length);for(const[p,y]of Object.entries(d))h(At[p]??p,y.length);return h("plugin",r.length),h("mods",r.filter(p=>p.kind==="mod"||p.components.includes("mod")).length),w}async function xt(o){try{return await zt(o)}catch{return{}}}export async function handleMarketRoutes(o,r,i,u,d){if(u==="/capabilities"&&o.method==="GET")return e(r,200,It()),!0;if(u==="/libraries"&&o.method==="GET")return e(r,200,{libraries:i.libraries?i.libraries.list():[]}),!0;if(u==="/libraries"&&o.method==="POST"){if(!i.libraries)return e(r,503,{error:"Libraries unavailable"}),!0;let a;try{a=JSON.parse(await g(o))}catch{return e(r,400,{error:"Invalid JSON body"}),!0}if(!a.path||!a.kind)return e(r,400,{error:'Missing "path" or "kind"'}),!0;if(!["skill","mcp","both"].includes(a.kind))return e(r,400,{error:'Invalid "kind" (skill|mcp|both)'}),!0;const t=i.libraries.add({path:a.path,kind:a.kind});return i.dataBus?.emit({key:"libraries"}),e(r,201,t),!0}const w=u.match(/^\/libraries\/(\d+)\/assets$/);if(w&&o.method==="GET"){if(!i.libraries)return e(r,503,{error:"Libraries unavailable"}),!0;const a=i.libraries.getById(Number(w[1]));if(!a)return e(r,404,{error:"Library not found"}),!0;const{plugins:t,skills:n,mcp:c,files:l}=await _(a.path),s=a.kind==="skill"||a.kind==="both"?t:[],m=a.kind==="mcp"||a.kind==="both"?c:[],f=a.kind==="skill"||a.kind==="both"?Object.values(l).flat():null;return e(r,200,{library:a,skills:n,mcp:m,files:f,plugins:s}),!0}const h=u.match(/^\/libraries\/(\d+)$/);if(h&&o.method==="DELETE"){if(!i.libraries)return e(r,503,{error:"Libraries unavailable"}),!0;const a=Number(h[1]),t=i.libraries.getById(a);return t&&await b(t.path),i.libraries.remove(a),i.dataBus?.emit({key:"libraries"}),i.dataBus?.emit({key:"market"}),e(r,200,{ok:!0}),!0}if(u==="/market"&&o.method==="GET"){if(!i.libraries)return e(r,503,{error:"Libraries unavailable"}),!0;const a=await Promise.all(i.libraries.list().map(t=>P(t,i.libraries.dataRoot)));return e(r,200,{items:a}),!0}if(u==="/market"&&o.method==="POST"){if(!i.libraries)return e(r,503,{error:"Libraries unavailable"}),!0;let a;try{a=JSON.parse(await g(o))}catch{return e(r,400,{error:"Invalid JSON body"}),!0}const t={libraries:i.libraries,dataRoot:i.libraries.dataRoot};try{if(a.kind==="dir"&&a.path){const n=await Nt(a.path,t);n.refreshed&&i.fingerprintCache?.invalidate(n.dir),await b(n.dir),i.dataBus?.emit({key:"market"}),e(r,201,{item:await P(i.libraries.getById(n.libraryId),i.libraries.dataRoot)})}else if(a.kind==="git"&&a.url){const n=await Ot(a.url,t);n.refreshed&&i.fingerprintCache?.invalidate(n.dir),await b(n.dir),i.dataBus?.emit({key:"market"}),e(r,201,{item:await P(i.libraries.getById(n.libraryId),i.libraries.dataRoot)})}else e(r,400,{error:'Invalid body (kind: "dir" + path | "git" + url)'})}catch(n){e(r,400,{error:n instanceof Error?n.message:"Import failed"})}return!0}if(u==="/market/check-updates"&&o.method==="POST"){if(!i.libraries)return e(r,503,{error:"Libraries unavailable"}),!0;let a={};const t=(await g(o)).trim();if(t)try{a=JSON.parse(t)}catch{return e(r,400,{error:"Invalid JSON body"}),!0}const n=i.libraries.list().filter(l=>!S(l.path,i.libraries.dataRoot)).filter(l=>!a.ids?.length||a.ids.includes(l.id));for(const l of n)await b(l.path);const c=await Ft(n.map(l=>({id:l.id,dir:l.path})));return i.dataBus?.emit({key:"market"}),e(r,200,{results:c}),!0}if(u==="/market/refresh"&&o.method==="POST"){if(!i.libraries)return e(r,503,{error:"Libraries unavailable"}),!0;let a={};const t=(await g(o)).trim();if(t)try{a=JSON.parse(t)}catch{return e(r,400,{error:"Invalid JSON body"}),!0}const n=i.libraries.list().filter(f=>!a.ids?.length||a.ids.includes(f.id)),c=[];for(const f of n.filter(k=>S(k.path,i.libraries.dataRoot))){const k=await Gt({libraries:i.libraries});c.push({id:f.id,status:k.error?"failed":"refreshed"})}const l=n.filter(f=>!S(f.path,i.libraries.dataRoot)).map(f=>({id:f.id,dir:f.path})),s=[...await Jt(l,{libraries:i.libraries,dataRoot:i.libraries.dataRoot}),...c],m=new Map(l.map(f=>[f.id,f.dir]));for(const f of s)if(f.status==="refreshed"){const k=m.get(f.id);k&&(i.fingerprintCache?.invalidate(k),await b(k))}return i.dataBus?.emit({key:"market"}),e(r,200,{results:s}),!0}const p=u.match(/^\/market\/(\d+)$/);if(p&&o.method==="DELETE"){if(!i.libraries)return e(r,503,{error:"Libraries unavailable"}),!0;const a=i.libraries.getById(Number(p[1]));if(!a)return e(r,404,{error:"Library not found"}),!0;if(S(a.path,i.libraries.dataRoot))return e(r,409,{error:"Built-in market is owned by weave and cannot be deleted",note:"It is re-materialized from @weavecode/templates on every daemon start."}),!0;if(!N(a.path,E(i.libraries.dataRoot)))return e(r,400,{error:"Not a market resource (legacy row \u2014 use DELETE /libraries/:id)"}),!0;let t;try{await(i.pluginSurface??V("claude")).removeMarketplace(a.path)}catch(n){t=`Host marketplace deregistration failed: ${n instanceof Error?n.message:String(n)}`}return await Lt(a.path),i.libraries.remove(a.id),await b(a.path),i.dataBus?.emit({key:"market"}),i.dataBus?.emit({key:"libraries"}),e(r,200,{ok:!0,removed:a.path,installedCopiesKept:!0,...t?{warning:t}:{},note:"The host cascade-uninstalls plugins installed from this market; other installed copies are kept."}),!0}const y=u.match(/^\/libraries\/(\d+)\/market-import$/);if(y&&o.method==="POST"){if(!i.libraries)return e(r,503,{error:"Libraries unavailable"}),!0;const a=i.libraries.getById(Number(y[1]));if(!a)return e(r,404,{error:"Library not found"}),!0;try{const t=a.path,n=await Tt(a,{libraries:i.libraries,dataRoot:i.libraries.dataRoot});await b(t),await b(n.dir),e(r,200,{item:await P(i.libraries.getById(n.libraryId),i.libraries.dataRoot)})}catch(t){e(r,400,{error:t instanceof Error?t.message:"Import failed"})}return!0}const T=u.match(/^\/projects\/(\d+)\/install$/);if(T&&o.method==="POST"){const a=i.projects.getById(Number(T[1]));let t;try{t=JSON.parse(await g(o))}catch{return e(r,400,{error:"Invalid JSON body"}),!0}if(!a&&Q(t))return e(r,404,{error:"Project not found"}),!0;const n=a?.path??"";try{if(t.category==="skill"){if(!t.name||!t.sourceDir)return e(r,400,{error:'Missing "name" or "sourceDir"'}),!0;const c=t.agent??"claude",l=t.scope==="user"?await et(t.sourceDir,t.name,c):await Z(n,t.sourceDir,t.name,c);e(r,201,{category:"skill",name:t.name,scope:t.scope??"project",agent:c,path:l})}else if(t.category&&K(t.category)){if(!t.name||!t.sourceFile)return e(r,400,{error:'Missing "name" or "sourceFile"'}),!0;const c=t.agent??"claude",l=t.scope??"project",s=await tt(n,t.category,t.name,t.sourceFile,c,l);e(r,201,{category:t.category,name:t.name,scope:l,agent:c,path:s})}else if(t.category==="mcp"){if(!t.name||!t.mcpConfig)return e(r,400,{error:'Missing "name" or "mcpConfig"'}),!0;const c=t.agent??"claude",l=v(c);if(!l)return e(r,400,{error:`Unsupported agent: ${c}`}),!0;const s=l.mcpScopes(),m=t.scope??s[0];if(!m||!s.includes(m))return e(r,400,{error:`MCP servers for ${c} are ${s.join("/")}-level only \u2014 scope "${t.scope}" is not available`}),!0;if(t.name in await l.mcpRead(m,n,j()))return I(r,new x(`MCP server "${t.name}" is already configured`)),!0;await l.mcpWrite(m,n,j(),t.name,t.mcpConfig),m==="project"&&await ut(n,{category:"mcp",name:t.name,agent:c}),e(r,201,{category:"mcp",name:t.name,scope:m,agent:c})}else if(t.category==="plugin"){if(!t.name||!t.sourceDir)return e(r,400,{error:'Missing "name" or "sourceDir"'}),!0;if(t.scope&&t.scope!=="user")return e(r,400,{error:'Plugin install currently only supports scope "user"'}),!0;const c=t.agent??"claude",l=W().find(f=>f.harness===c);if(!l)return e(r,400,{error:`No plugin install surface for runtime: ${c}`}),!0;const s=c==="claude"&&i.pluginSurface?i.pluginSurface:l.surface,m=await Et(s,{dir:t.sourceDir,name:t.name,version:t.version,description:t.description});i.dataBus?.emit({key:"toolkit"}),e(r,201,{category:"plugin",key:m.key,scope:"user",agent:c,alreadyInstalled:m.alreadyInstalled})}else e(r,400,{error:'Invalid "category" (skill|mcp|plugin|command|agent|workflow|rule|output-style)'})}catch(c){I(r,c)}return!0}const C=u.match(/^\/projects\/(\d+)\/mcp\/builtin$/);if(C&&o.method==="POST"){const a=i.projects.getById(Number(C[1]));let t;try{t=JSON.parse(await g(o))}catch{return e(r,400,{error:"Invalid JSON body"}),!0}const n=Pt.find(f=>f.name===t.name);if(!n)return e(r,404,{error:`Unknown built-in MCP server: ${t.name??""}`}),!0;if(!a)return e(r,404,{error:"Project not found"}),!0;const c=t.agent??"claude",l=v(c);if(!l||!l.mcpScopes().includes("user"))return e(r,400,{error:`MCP servers for ${c} have no user scope`}),!0;const s=i.auth?.getLocalToken()??"",m={type:"http",url:`http://127.0.0.1:${i.port}${n.path}`,...s?{headers:{"x-weave-local":s}}:{}};try{await l.mcpWrite("user",a.path,j(),n.name,m),e(r,201,{category:"mcp",name:n.name,scope:"user",agent:c})}catch(f){e(r,400,{error:f instanceof Error?f.message:"Install failed"})}return!0}const $=u.match(/^\/projects\/(\d+)\/uninstall$/);if($&&o.method==="POST"){const a=i.projects.getById(Number($[1]));let t;try{t=JSON.parse(await g(o))}catch{return e(r,400,{error:"Invalid JSON body"}),!0}if(!a&&Q(t))return e(r,404,{error:"Project not found"}),!0;const n=a?.path??"";try{if(t.category==="skill"){if(!t.name)return e(r,400,{error:'Missing "name"'}),!0;const c=t.agent??"claude";t.scope==="user"?await at(t.name,c):await q(n,t.name,c)}else if(t.category&&K(t.category)){if(!t.name)return e(r,400,{error:'Missing "name"'}),!0;await rt(n,t.category,t.name,t.agent??"claude",t.scope??"project")}else if(t.category==="mcp"){if(!t.name)return e(r,400,{error:'Missing "name"'}),!0;const c=t.agent??"claude",l=v(c);if(!l)return e(r,400,{error:`Unsupported agent: ${c}`}),!0;const s=l.mcpScopes(),m=t.scope??s[0];if(!m||!s.includes(m))return e(r,400,{error:`MCP servers for ${c} are ${s.join("/")}-level only \u2014 scope "${t.scope}" is not available`}),!0;if(!await l.mcpRemove(m,n,j(),t.name))return I(r,new M(`MCP server "${t.name}" is not configured`)),!0;m==="project"&&await st(n,{category:"mcp",name:t.name,agent:c})}else return e(r,400,{error:'Invalid "category" (skill|mcp|command|agent|workflow|rule|output-style)'}),!0;e(r,200,{ok:!0})}catch(c){I(r,c)}return!0}const B=u.match(/^\/projects\/(\d+)\/asset-file$/);if(B&&o.method==="GET"){const a=i.projects.getById(Number(B[1]));if(!a)return e(r,404,{error:"Project not found"}),!0;const t=d.searchParams.get("path");if(!t)return e(r,400,{error:'Missing "path" query parameter'}),!0;try{const n=await mt(a.path,t);e(r,200,{path:t,content:n.content,size:n.size})}catch(n){O(r,n)}return!0}if(u==="/global-file"&&o.method==="GET"){const a=d.searchParams.get("path");if(!a)return e(r,400,{error:'Missing "path" query parameter'}),!0;try{const t=await ft(a);e(r,200,{path:a,content:t.content,size:t.size})}catch(t){O(r,t)}return!0}const F=u.match(/^\/projects\/(\d+)\/mcp$/);if(F&&o.method==="GET"){const a=i.projects.getById(Number(F[1]));return a?(e(r,200,{rows:await gt(a.path)}),!0):(e(r,404,{error:"Project not found"}),!0)}const J=u.match(/^\/projects\/(\d+)\/harness-checks$/);if(J&&o.method==="GET"){const a=i.projects.getById(Number(J[1]));return a?(e(r,200,{checks:await Y(a.path)}),!0):(e(r,404,{error:"Project not found"}),!0)}if(u.match(/^\/projects\/(\d+)\/skills\/global$/)&&o.method==="GET")return e(r,200,{groups:await it()}),!0;if(u.match(/^\/projects\/(\d+)\/skills\/global\/files$/)&&o.method==="GET"){const a=d.searchParams.get("source"),t=d.searchParams.get("name"),n=d.searchParams.get("pluginKey")??void 0;if(!a||!t)return e(r,400,{error:'Missing "source" or "name" query parameter'}),!0;const c=await H(a,t,n);return c?(e(r,200,{files:await ot(c)}),!0):(e(r,404,{error:"Skill not found"}),!0)}if(u.match(/^\/projects\/(\d+)\/skills\/global\/file$/)&&o.method==="GET"){const a=d.searchParams.get("source"),t=d.searchParams.get("name"),n=d.searchParams.get("pluginKey")??void 0,c=d.searchParams.get("path");if(!a||!t||!c)return e(r,400,{error:'Missing "source", "name" or "path" query parameter'}),!0;const l=await H(a,t,n);if(!l)return e(r,404,{error:"Skill not found"}),!0;try{const s=await nt(l,c);e(r,200,{path:c,content:s.content,size:s.size})}catch(s){O(r,s)}return!0}const G=u.match(/^\/projects\/(\d+)\/plugins\/state$/);if(G){const a=i.projects.getById(Number(G[1]));if(!a)return e(r,404,{error:"Project not found"}),!0;if(o.method==="GET")return e(r,200,{rows:await Mt(a.path)}),!0;if(o.method==="PUT"){let t;try{t=JSON.parse(await g(o))}catch{return e(r,400,{error:"Invalid JSON body"}),!0}if(!A(t.runtime)||!t.key||!t.scope||!["user","project","local"].includes(t.scope)||!t.state||!["on","off","inherit"].includes(t.state))return e(r,400,{error:'Missing or invalid "runtime"/"key"/"scope" (user|project|local)/"state" (on|off|inherit)'}),!0;const n=t.scope,c=t.state;try{const l=W().find(s=>s.harness===t.runtime);if(l)await(t.runtime==="claude"&&i.pluginSurface?i.pluginSurface:l.surface).setEnabledOverride(a.path,n,t.key,c);else{const s=Ut().find(m=>m.harness===t.runtime);if(!s||n!=="user"||c==="inherit")return e(r,400,{error:"This runtime only supports user-scope on/off overrides"}),!0;await s.state.writeGlobalEnabled(t.key,c==="on")}i.dataBus?.emit({key:"toolkit"}),e(r,200,{ok:!0})}catch(l){e(r,400,{error:l instanceof Error?l.message:"Plugin state write failed"})}return!0}}if(u.match(/^\/projects\/(\d+)\/plugins\/uninstall$/)&&o.method==="POST"){let a;try{a=JSON.parse(await g(o))}catch{return e(r,400,{error:"Invalid JSON body"}),!0}if(!A(a.runtime)||!a.key)return e(r,400,{error:'Missing or invalid "runtime"/"key"'}),!0;try{const t=a.runtime==="claude"&&i.pluginSurface?i.pluginSurface:V(a.runtime),{name:n,market:c}=t.parsePluginKey(a.key);await t.uninstall(n,c),e(r,200,{ok:!0})}catch(t){e(r,400,{error:t instanceof Error?t.message:"Plugin uninstall failed"})}return!0}const L=u.match(/^\/projects\/(\d+)\/mcp\/enable$/);if(L){const a=i.projects.getById(Number(L[1]));if(!a)return e(r,404,{error:"Project not found"}),!0;if(o.method==="PUT"){let t;try{t=JSON.parse(await g(o))}catch{return e(r,400,{error:"Invalid JSON body"}),!0}return!t.name||!t.state?(e(r,400,{error:'Missing "name" or "state"'}),!0):["on","off","inherit"].includes(t.state)?(await ht(a.path,t.name,t.state),e(r,200,{ok:!0}),!0):(e(r,400,{error:'Invalid "state" (on|off|inherit)'}),!0)}}const R=u.match(/^\/projects\/(\d+)\/updates$/);if(R&&o.method==="GET"){const a=i.projects.getById(Number(R[1]));if(!a)return e(r,404,{error:"Project not found"}),!0;const t=i.fingerprintCache??new z;if(!i.libraries){const c=await St(a.path,t),l=await jt(a.path);return e(r,200,{skills:[],mcp:[],files:[],pluginTemplates:c,initFiles:l,available:c.filter(s=>s.outdated).length+l.filter(s=>s.outdated&&s.syncClass==="auto").length,needsInit:vt(l)}),!0}const n=await wt(a.path,i.libraries.list(),t);return e(r,200,n),!0}const D=u.match(/^\/projects\/(\d+)\/update$/);if(D&&o.method==="POST"){const a=i.projects.getById(Number(D[1]));if(!a)return e(r,404,{error:"Project not found"}),!0;if(!i.libraries)return e(r,503,{error:"Libraries unavailable"}),!0;let t;try{t=JSON.parse(await g(o))}catch{return e(r,400,{error:"Invalid JSON body"}),!0}if(!t.category||!t.name||!t.scope)return e(r,400,{error:'Missing "category", "name", or "scope"'}),!0;if(!["skill","mcp","command","agent","workflow","rule","output-style"].includes(t.category))return e(r,400,{error:'Invalid "category"'}),!0;try{const c=await kt(i.libraries.list());await bt(a.path,{category:t.category,name:t.name,scope:t.scope,agent:t.agent},c),e(r,200,{ok:!0,category:t.category,name:t.name,scope:t.scope})}catch(c){e(r,400,{error:c instanceof Error?c.message:"Update failed"})}return!0}const U=u.match(/^\/projects\/(\d+)\/sync-all$/);if(U&&o.method==="POST"){const a=i.projects.getById(Number(U[1]));if(!a)return e(r,404,{error:"Project not found"}),!0;if(!i.libraries)return e(r,503,{error:"Libraries unavailable"}),!0;try{const t=i.fingerprintCache??new z,n=await yt(a.path,i.libraries.list(),t);let c=n;try{const l=i.hookPlugins?.list().map(m=>m.id)??[],s=Rt(a,l,{projects:i.projects});c={...n,pluginSync:{syncedAt:s}}}catch{}e(r,200,c),i.updatesRefresher?.refreshNow(!0)}catch(t){e(r,400,{error:t instanceof Error?t.message:"Sync failed"})}return!0}return!1}
|
|
1
|
+
import{homedir as v}from"node:os";import Q from"node:path";import{checkHarness as X,isHarness as A}from"@weavecode/core";import{readBody as h,sendJson as t}from"../http.js";import{FingerprintCache as z}from"../../install/fingerprint.js";import{installSkill as Y,uninstallSkill as Z,installFileAsset as ee,uninstallFileAsset as re,InstallConflictError as x,AssetNotFoundError as E}from"../../install/installer.js";import{isFileAssetCategory as H}from"../../install/file-assets.js";import{installGlobalSkill as te,uninstallGlobalSkill as ae,readGlobalSkillGroups as oe,resolveGlobalSkillDir as q,listGlobalSkillFiles as ie,readGlobalSkillFile as ne,ClaudeJsonCorruptError as se}from"../../install/global-config.js";import{CodexTomlCorruptError as le}from"../../install/codex-toml.js";import{forgetInstalled as ce,recordInstalled as ue}from"../../install/install-ledger.js";import{readProjectFile as me,readGlobalFile as de,PathEscapeError as pe,FileTooLargeError as fe}from"../../install/reader.js";import{readMcpRows as he}from"../../install/mcp-rows.js";import{setMcpEnableOverride as ge}from"../../install/settings-mcp.js";import{applyUpdate as ye,syncAll as be}from"../../install/apply-update.js";import{buildLibraryIndex as ke}from"../../install/library-index.js";import{detectUpdates as we}from"../../install/updates.js";import{detectPluginTemplateUpdates as Se}from"../../install/plugin-templates.js";import{detectInitFileUpdates as ve,needsInit as Ie}from"../../install/init-files.js";import{getLibraryScan as K,invalidateScan as y}from"../../install/scan-cache.js";import{installCapabilities as Pe}from"../../install/capabilities.js";import{BUILTIN_MCP_SERVERS as je}from"../../install/builtin-mcp.js";import{readPluginRows as Ee}from"../../install/plugin-rows.js";import{installPluginPack as Ne}from"../../install/plugin-install.js";import{importFromDir as Oe,importFromGit as Te,importLibraryIntoMarket as $e}from"../../market/import.js";import{marketDir as N,readManifest as Be}from"../../market/manifest.js";import{marketIdOf as Me}from"../../market/identity.js";import{isInsideDir as O,toRelPosix as Ce}from"../../market/resolve.js";import{checkMarketUpdates as Je}from"../../market/updates.js";import{refreshMarketItems as Re}from"../../market/refresh.js";import{ensureBuiltinMarket as Ge,isBuiltinMarketDir as S}from"../../market/builtin.js";import{removeInstalled as Le}from"../../market/install-link.js";import{syncPlugins as Fe}from"../../hooks/plugin-project-state.js";import{assetSurfaces as De,pluginStateSurfaces as Ue,pluginSurfaces as W,pluginSurfaceFor as _}from"../../surfaces.js";function V(i){return i.scope==="user"||i.category==="plugin"?!1:i.category==="mcp"?!!I(i.agent)?.mcpScopes().includes("project"):!0}function I(i){const r=i??"claude";return De().find(o=>o.harness===r)}function P(i,r){r instanceof x?i.statusCode=409:r instanceof E?i.statusCode=404:r instanceof se||r instanceof le?i.statusCode=500:i.statusCode=400,i.setHeader("content-type","application/json"),i.end(JSON.stringify({error:r instanceof Error?r.message:"Install failed"}))}function T(i,r){r instanceof pe?i.statusCode=403:r instanceof fe?i.statusCode=413:r instanceof E?i.statusCode=404:i.statusCode=400,i.setHeader("content-type","application/json"),i.end(JSON.stringify({error:r instanceof Error?r.message:"Read failed"}))}async function j(i,r){const o=O(i.path,N(r)),u=o?await Be(i.path):null,p=S(i.path,r);return{id:i.id,kind:i.kind,addedAt:i.addedAt,path:i.path,relPath:O(i.path,r)?Ce(i.path,r):null,resourceId:o?Q.basename(i.path):null,managed:o,builtin:p,namespace:o?Me(i.path,N(r)):void 0,legacy:!u&&!p,source:p?"builtin":u?.source??"legacy",origin:u?.origin??null,importedAt:u?.importedAt??null,commit:u?.commit??null,tags:await xe(i.path)}}const Ae={command:"command",agent:"agent",workflow:"workflow",rule:"rules","output-style":"output-style"};async function ze(i){const{plugins:r,skills:o,mcp:u,files:p}=await K(i),w={},g=(f,b)=>{b>0&&(w[f]=(w[f]??0)+b)};g("skill",o.length),g("mcp",u.length);for(const[f,b]of Object.entries(p))g(Ae[f]??f,b.length);return g("plugin",r.length),g("mods",r.filter(f=>f.kind==="mod"||f.components.includes("mod")).length),w}async function xe(i){try{return await ze(i)}catch{return{}}}export async function handleMarketRoutes(i,r,o,u,p){if(u==="/capabilities"&&i.method==="GET")return t(r,200,Pe()),!0;if(u==="/libraries"&&i.method==="GET")return t(r,200,{libraries:o.libraries?o.libraries.list():[]}),!0;if(u==="/libraries"&&i.method==="POST"){if(!o.libraries)return t(r,503,{error:"Libraries unavailable"}),!0;let a;try{a=JSON.parse(await h(i))}catch{return t(r,400,{error:"Invalid JSON body"}),!0}if(!a.path||!a.kind)return t(r,400,{error:'Missing "path" or "kind"'}),!0;if(!["skill","mcp","both"].includes(a.kind))return t(r,400,{error:'Invalid "kind" (skill|mcp|both)'}),!0;const e=o.libraries.add({path:a.path,kind:a.kind});return o.dataBus?.emit({key:"libraries"}),t(r,201,e),!0}const w=u.match(/^\/libraries\/(\d+)\/assets$/);if(w&&i.method==="GET"){if(!o.libraries)return t(r,503,{error:"Libraries unavailable"}),!0;const a=o.libraries.getById(Number(w[1]));if(!a)return t(r,404,{error:"Library not found"}),!0;const{plugins:e,skills:n,mcp:s,files:l}=await K(a.path),c=a.kind==="skill"||a.kind==="both"?e:[],m=a.kind==="mcp"||a.kind==="both"?s:[],d=a.kind==="skill"||a.kind==="both"?Object.values(l).flat():null;return t(r,200,{library:a,skills:n,mcp:m,files:d,plugins:c}),!0}const g=u.match(/^\/libraries\/(\d+)$/);if(g&&i.method==="DELETE"){if(!o.libraries)return t(r,503,{error:"Libraries unavailable"}),!0;const a=Number(g[1]),e=o.libraries.getById(a);return e&&await y(e.path),o.libraries.remove(a),o.dataBus?.emit({key:"libraries"}),o.dataBus?.emit({key:"market"}),t(r,200,{ok:!0}),!0}if(u==="/market"&&i.method==="GET"){if(!o.libraries)return t(r,503,{error:"Libraries unavailable"}),!0;const a=await Promise.all(o.libraries.list().map(e=>j(e,o.libraries.dataRoot)));return t(r,200,{items:a}),!0}if(u==="/market"&&i.method==="POST"){if(!o.libraries)return t(r,503,{error:"Libraries unavailable"}),!0;let a;try{a=JSON.parse(await h(i))}catch{return t(r,400,{error:"Invalid JSON body"}),!0}const e={libraries:o.libraries,dataRoot:o.libraries.dataRoot};try{if(a.kind==="dir"&&a.path){const n=await Oe(a.path,e);n.refreshed&&o.fingerprintCache?.invalidate(n.dir),await y(n.dir),o.dataBus?.emit({key:"market"}),t(r,201,{item:await j(o.libraries.getById(n.libraryId),o.libraries.dataRoot)})}else if(a.kind==="git"&&a.url){const n=await Te(a.url,e);n.refreshed&&o.fingerprintCache?.invalidate(n.dir),await y(n.dir),o.dataBus?.emit({key:"market"}),t(r,201,{item:await j(o.libraries.getById(n.libraryId),o.libraries.dataRoot)})}else t(r,400,{error:'Invalid body (kind: "dir" + path | "git" + url)'})}catch(n){t(r,400,{error:n instanceof Error?n.message:"Import failed"})}return!0}if(u==="/market/check-updates"&&i.method==="POST"){if(!o.libraries)return t(r,503,{error:"Libraries unavailable"}),!0;let a={};const e=(await h(i)).trim();if(e)try{a=JSON.parse(e)}catch{return t(r,400,{error:"Invalid JSON body"}),!0}const n=o.libraries.list().filter(l=>!S(l.path,o.libraries.dataRoot)).filter(l=>!a.ids?.length||a.ids.includes(l.id));for(const l of n)await y(l.path);const s=await Je(n.map(l=>({id:l.id,dir:l.path})));return o.dataBus?.emit({key:"market"}),t(r,200,{results:s}),!0}if(u==="/market/refresh"&&i.method==="POST"){if(!o.libraries)return t(r,503,{error:"Libraries unavailable"}),!0;let a={};const e=(await h(i)).trim();if(e)try{a=JSON.parse(e)}catch{return t(r,400,{error:"Invalid JSON body"}),!0}const n=o.libraries.list().filter(d=>!a.ids?.length||a.ids.includes(d.id)),s=[];for(const d of n.filter(k=>S(k.path,o.libraries.dataRoot))){const k=await Ge({libraries:o.libraries});s.push({id:d.id,status:k.error?"failed":"refreshed"})}const l=n.filter(d=>!S(d.path,o.libraries.dataRoot)).map(d=>({id:d.id,dir:d.path})),c=[...await Re(l,{libraries:o.libraries,dataRoot:o.libraries.dataRoot}),...s],m=new Map(l.map(d=>[d.id,d.dir]));for(const d of c)if(d.status==="refreshed"){const k=m.get(d.id);k&&(o.fingerprintCache?.invalidate(k),await y(k))}return o.dataBus?.emit({key:"market"}),t(r,200,{results:c}),!0}const f=u.match(/^\/market\/(\d+)$/);if(f&&i.method==="DELETE"){if(!o.libraries)return t(r,503,{error:"Libraries unavailable"}),!0;const a=o.libraries.getById(Number(f[1]));if(!a)return t(r,404,{error:"Library not found"}),!0;if(S(a.path,o.libraries.dataRoot))return t(r,409,{error:"Built-in market is owned by weave and cannot be deleted",note:"It is re-materialized from @weavecode/templates on every daemon start."}),!0;if(!O(a.path,N(o.libraries.dataRoot)))return t(r,400,{error:"Not a market resource (legacy row \u2014 use DELETE /libraries/:id)"}),!0;let e;try{await(o.pluginSurface??_("claude")).removeMarketplace(a.path)}catch(n){e=`Host marketplace deregistration failed: ${n instanceof Error?n.message:String(n)}`}return await Le(a.path),o.libraries.remove(a.id),await y(a.path),o.dataBus?.emit({key:"market"}),o.dataBus?.emit({key:"libraries"}),t(r,200,{ok:!0,removed:a.path,installedCopiesKept:!0,...e?{warning:e}:{},note:"The host cascade-uninstalls plugins installed from this market; other installed copies are kept."}),!0}const b=u.match(/^\/libraries\/(\d+)\/market-import$/);if(b&&i.method==="POST"){if(!o.libraries)return t(r,503,{error:"Libraries unavailable"}),!0;const a=o.libraries.getById(Number(b[1]));if(!a)return t(r,404,{error:"Library not found"}),!0;try{const e=a.path,n=await $e(a,{libraries:o.libraries,dataRoot:o.libraries.dataRoot});await y(e),await y(n.dir),t(r,200,{item:await j(o.libraries.getById(n.libraryId),o.libraries.dataRoot)})}catch(e){t(r,400,{error:e instanceof Error?e.message:"Import failed"})}return!0}const $=u.match(/^\/projects\/(\d+)\/install$/);if($&&i.method==="POST"){const a=o.projects.getById(Number($[1]));let e;try{e=JSON.parse(await h(i))}catch{return t(r,400,{error:"Invalid JSON body"}),!0}if(!a&&V(e))return t(r,404,{error:"Project not found"}),!0;const n=a?.path??"";try{if(e.category==="skill"){if(!e.name||!e.sourceDir)return t(r,400,{error:'Missing "name" or "sourceDir"'}),!0;const s=e.agent??"claude",l=e.scope==="user"?await te(e.sourceDir,e.name,s):await Y(n,e.sourceDir,e.name,s);t(r,201,{category:"skill",name:e.name,scope:e.scope??"project",agent:s,path:l})}else if(e.category&&H(e.category)){if(!e.name||!e.sourceFile)return t(r,400,{error:'Missing "name" or "sourceFile"'}),!0;const s=e.agent??"claude",l=e.scope??"project",c=await ee(n,e.category,e.name,e.sourceFile,s,l);t(r,201,{category:e.category,name:e.name,scope:l,agent:s,path:c})}else if(e.category==="mcp"){if(!e.name||!e.mcpConfig)return t(r,400,{error:'Missing "name" or "mcpConfig"'}),!0;const s=e.agent??"claude",l=I(s);if(!l)return t(r,400,{error:`Unsupported agent: ${s}`}),!0;const c=l.mcpScopes(),m=e.scope??c[0];if(!m||!c.includes(m))return t(r,400,{error:`MCP servers for ${s} are ${c.join("/")}-level only \u2014 scope "${e.scope}" is not available`}),!0;if(e.name in await l.mcpRead(m,n,v()))return P(r,new x(`MCP server "${e.name}" is already configured`)),!0;await l.mcpWrite(m,n,v(),e.name,e.mcpConfig),m==="project"&&await ue(n,{category:"mcp",name:e.name,agent:s}),t(r,201,{category:"mcp",name:e.name,scope:m,agent:s})}else if(e.category==="plugin"){if(!e.name||!e.sourceDir)return t(r,400,{error:'Missing "name" or "sourceDir"'}),!0;if(e.scope&&e.scope!=="user")return t(r,400,{error:'Plugin install currently only supports scope "user"'}),!0;const s=e.agent??"claude",l=W().find(d=>d.harness===s);if(!l)return t(r,400,{error:`No plugin install surface for runtime: ${s}`}),!0;const c=s==="claude"&&o.pluginSurface?o.pluginSurface:l.surface,m=await Ne(c,{dir:e.sourceDir,name:e.name,version:e.version,description:e.description});o.dataBus?.emit({key:"toolkit"}),t(r,201,{category:"plugin",key:m.key,scope:"user",agent:s,alreadyInstalled:m.alreadyInstalled})}else t(r,400,{error:'Invalid "category" (skill|mcp|plugin|command|agent|workflow|rule|output-style)'})}catch(s){P(r,s)}return!0}const B=u.match(/^\/projects\/(\d+)\/mcp\/builtin$/);if(B&&i.method==="POST"){const a=o.projects.getById(Number(B[1]));let e;try{e=JSON.parse(await h(i))}catch{return t(r,400,{error:"Invalid JSON body"}),!0}const n=je.find(d=>d.name===e.name);if(!n)return t(r,404,{error:`Unknown built-in MCP server: ${e.name??""}`}),!0;if(!a)return t(r,404,{error:"Project not found"}),!0;const s=e.agent??"claude",l=I(s);if(!l||!l.mcpScopes().includes("user"))return t(r,400,{error:`MCP servers for ${s} have no user scope`}),!0;const c=o.auth?.getLocalToken()??"",m={type:"http",url:`http://127.0.0.1:${o.port}${n.path}`,...c?{headers:{"x-weave-local":c}}:{}};try{await l.mcpWrite("user",a.path,v(),n.name,m),t(r,201,{category:"mcp",name:n.name,scope:"user",agent:s})}catch(d){t(r,400,{error:d instanceof Error?d.message:"Install failed"})}return!0}const M=u.match(/^\/projects\/(\d+)\/uninstall$/);if(M&&i.method==="POST"){const a=o.projects.getById(Number(M[1]));let e;try{e=JSON.parse(await h(i))}catch{return t(r,400,{error:"Invalid JSON body"}),!0}if(!a&&V(e))return t(r,404,{error:"Project not found"}),!0;const n=a?.path??"";try{if(e.category==="skill"){if(!e.name)return t(r,400,{error:'Missing "name"'}),!0;const s=e.agent??"claude";e.scope==="user"?await ae(e.name,s):await Z(n,e.name,s)}else if(e.category&&H(e.category)){if(!e.name)return t(r,400,{error:'Missing "name"'}),!0;await re(n,e.category,e.name,e.agent??"claude",e.scope??"project")}else if(e.category==="mcp"){if(!e.name)return t(r,400,{error:'Missing "name"'}),!0;const s=e.agent??"claude",l=I(s);if(!l)return t(r,400,{error:`Unsupported agent: ${s}`}),!0;const c=l.mcpScopes(),m=e.scope??c[0];if(!m||!c.includes(m))return t(r,400,{error:`MCP servers for ${s} are ${c.join("/")}-level only \u2014 scope "${e.scope}" is not available`}),!0;if(!await l.mcpRemove(m,n,v(),e.name))return P(r,new E(`MCP server "${e.name}" is not configured`)),!0;m==="project"&&await ce(n,{category:"mcp",name:e.name,agent:s})}else return t(r,400,{error:'Invalid "category" (skill|mcp|command|agent|workflow|rule|output-style)'}),!0;t(r,200,{ok:!0})}catch(s){P(r,s)}return!0}const C=u.match(/^\/projects\/(\d+)\/asset-file$/);if(C&&i.method==="GET"){const a=o.projects.getById(Number(C[1]));if(!a)return t(r,404,{error:"Project not found"}),!0;const e=p.searchParams.get("path");if(!e)return t(r,400,{error:'Missing "path" query parameter'}),!0;try{const n=await me(a.path,e);t(r,200,{path:e,content:n.content,size:n.size})}catch(n){T(r,n)}return!0}if(u==="/global-file"&&i.method==="GET"){const a=p.searchParams.get("path");if(!a)return t(r,400,{error:'Missing "path" query parameter'}),!0;try{const e=await de(a);t(r,200,{path:a,content:e.content,size:e.size})}catch(e){T(r,e)}return!0}const J=u.match(/^\/projects\/(\d+)\/mcp$/);if(J&&i.method==="GET"){const a=o.projects.getById(Number(J[1]));return a?(t(r,200,{rows:await he(a.path)}),!0):(t(r,404,{error:"Project not found"}),!0)}const R=u.match(/^\/projects\/(\d+)\/harness-checks$/);if(R&&i.method==="GET"){const a=o.projects.getById(Number(R[1]));return a?(t(r,200,{checks:await X(a.path)}),!0):(t(r,404,{error:"Project not found"}),!0)}if(u.match(/^\/projects\/(\d+)\/skills\/global$/)&&i.method==="GET")return t(r,200,{groups:await oe()}),!0;if(u.match(/^\/projects\/(\d+)\/skills\/global\/files$/)&&i.method==="GET"){const a=p.searchParams.get("source"),e=p.searchParams.get("name"),n=p.searchParams.get("pluginKey")??void 0;if(!a||!e)return t(r,400,{error:'Missing "source" or "name" query parameter'}),!0;const s=await q(a,e,n);return s?(t(r,200,{files:await ie(s)}),!0):(t(r,404,{error:"Skill not found"}),!0)}if(u.match(/^\/projects\/(\d+)\/skills\/global\/file$/)&&i.method==="GET"){const a=p.searchParams.get("source"),e=p.searchParams.get("name"),n=p.searchParams.get("pluginKey")??void 0,s=p.searchParams.get("path");if(!a||!e||!s)return t(r,400,{error:'Missing "source", "name" or "path" query parameter'}),!0;const l=await q(a,e,n);if(!l)return t(r,404,{error:"Skill not found"}),!0;try{const c=await ne(l,s);t(r,200,{path:s,content:c.content,size:c.size})}catch(c){T(r,c)}return!0}const G=u.match(/^\/projects\/(\d+)\/plugins\/state$/);if(G){const a=o.projects.getById(Number(G[1]));if(!a)return t(r,404,{error:"Project not found"}),!0;if(i.method==="GET")return t(r,200,{rows:await Ee(a.path)}),!0;if(i.method==="PUT"){let e;try{e=JSON.parse(await h(i))}catch{return t(r,400,{error:"Invalid JSON body"}),!0}if(!A(e.runtime)||!e.key||!e.scope||!["user","project","local"].includes(e.scope)||!e.state||!["on","off","inherit"].includes(e.state))return t(r,400,{error:'Missing or invalid "runtime"/"key"/"scope" (user|project|local)/"state" (on|off|inherit)'}),!0;const n=e.scope,s=e.state;try{const l=W().find(c=>c.harness===e.runtime);if(l)await(e.runtime==="claude"&&o.pluginSurface?o.pluginSurface:l.surface).setEnabledOverride(a.path,n,e.key,s);else{const c=Ue().find(m=>m.harness===e.runtime);if(!c||n!=="user"||s==="inherit")return t(r,400,{error:"This runtime only supports user-scope on/off overrides"}),!0;await c.state.writeGlobalEnabled(e.key,s==="on")}o.dataBus?.emit({key:"toolkit"}),t(r,200,{ok:!0})}catch(l){t(r,400,{error:l instanceof Error?l.message:"Plugin state write failed"})}return!0}}if(u.match(/^\/projects\/(\d+)\/plugins\/uninstall$/)&&i.method==="POST"){let a;try{a=JSON.parse(await h(i))}catch{return t(r,400,{error:"Invalid JSON body"}),!0}if(!A(a.runtime)||!a.key)return t(r,400,{error:'Missing or invalid "runtime"/"key"'}),!0;try{const e=a.runtime==="claude"&&o.pluginSurface?o.pluginSurface:_(a.runtime),{name:n,market:s}=e.parsePluginKey(a.key);await e.uninstall(n,s),t(r,200,{ok:!0})}catch(e){t(r,400,{error:e instanceof Error?e.message:"Plugin uninstall failed"})}return!0}const L=u.match(/^\/projects\/(\d+)\/mcp\/enable$/);if(L){const a=o.projects.getById(Number(L[1]));if(!a)return t(r,404,{error:"Project not found"}),!0;if(i.method==="PUT"){let e;try{e=JSON.parse(await h(i))}catch{return t(r,400,{error:"Invalid JSON body"}),!0}return!e.name||!e.state?(t(r,400,{error:'Missing "name" or "state"'}),!0):["on","off","inherit"].includes(e.state)?(await ge(a.path,e.name,e.state),t(r,200,{ok:!0}),!0):(t(r,400,{error:'Invalid "state" (on|off|inherit)'}),!0)}}const F=u.match(/^\/projects\/(\d+)\/updates$/);if(F&&i.method==="GET"){const a=o.projects.getById(Number(F[1]));if(!a)return t(r,404,{error:"Project not found"}),!0;const e=o.fingerprintCache??new z;if(!o.libraries){const s=await Se(a.path,e),l=await ve(a.path);return t(r,200,{skills:[],mcp:[],files:[],pluginTemplates:s,initFiles:l,available:s.filter(c=>c.outdated).length+l.filter(c=>c.outdated&&c.syncClass==="auto").length,needsInit:Ie(l)}),!0}const n=await we(a.path,o.libraries.list(),e);return t(r,200,n),!0}const D=u.match(/^\/projects\/(\d+)\/update$/);if(D&&i.method==="POST"){const a=o.projects.getById(Number(D[1]));if(!a)return t(r,404,{error:"Project not found"}),!0;if(!o.libraries)return t(r,503,{error:"Libraries unavailable"}),!0;let e;try{e=JSON.parse(await h(i))}catch{return t(r,400,{error:"Invalid JSON body"}),!0}if(!e.category||!e.name||!e.scope)return t(r,400,{error:'Missing "category", "name", or "scope"'}),!0;if(!["skill","mcp","command","agent","workflow","rule","output-style"].includes(e.category))return t(r,400,{error:'Invalid "category"'}),!0;try{const n=await ke(o.libraries.list());await ye(a.path,{category:e.category,name:e.name,scope:e.scope,agent:e.agent},n),t(r,200,{ok:!0,category:e.category,name:e.name,scope:e.scope})}catch(n){t(r,400,{error:n instanceof Error?n.message:"Update failed"})}return!0}const U=u.match(/^\/projects\/(\d+)\/sync-all$/);if(U&&i.method==="POST"){const a=o.projects.getById(Number(U[1]));if(!a)return t(r,404,{error:"Project not found"}),!0;if(!o.libraries)return t(r,503,{error:"Libraries unavailable"}),!0;try{const e=o.fingerprintCache??new z,n=await be(a.path,o.libraries.list(),e);let s=n;try{const l=o.hookPlugins?.list().map(m=>m.id)??[],c=Fe(a,l,{projects:o.projects});s={...n,pluginSync:{syncedAt:c}}}catch{}t(r,200,s),o.updatesRefresher?.refreshNow(!0)}catch(e){t(r,400,{error:e instanceof Error?e.message:"Sync failed"})}return!0}return!1}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{z as i}from"zod";import{nextRunAt as E,parseCron as
|
|
1
|
+
import{z as i}from"zod";import{nextRunAt as E,parseCron as x}from"../cron.js";import{validateOrchestration as R}from"../../hooks/orchestration-graph.js";import{graphDirections as S,toRunSummary as j}from"../../repositories/orchestrations.js";import{readBody as v,readJson as k,sendJson as e}from"../http.js";const B=i.object({id:i.string().min(1).max(128),kind:i.enum(["session","webhook","trigger"]),webhookToken:i.string().min(1).max(200).optional(),url:i.string().max(2e3).optional(),secret:i.string().max(400).optional(),autoFire:i.boolean().optional()}),w=i.object({name:i.string().min(1).max(200),startText:i.string().max(2e4).optional(),projectId:i.number().int().optional(),nodes:i.array(B).min(1),edges:i.array(i.object({id:i.string().min(1).max(64),from:i.string().min(1),to:i.string().min(1),text:i.string().max(2e4),extract:i.string().max(4e3).optional(),condition:i.string().max(4e3).optional(),when:i.string().max(500).optional()})),cron:i.string().max(200).nullish(),enabled:i.boolean().optional()}),N=w.partial(),P=i.object({text:i.string().min(1).max(2e4).optional(),entries:i.array(i.string().min(1)).optional()}),O=i.object({nodeId:i.string().min(1).max(128)}),$=new Set(["running","done","failed","cancelled","interrupted"]);function g(s,r){const t=s.searchParams.get(r);if(t==null||t==="")return;const c=Number(t);return Number.isFinite(c)?c:void 0}function I(s){const r=s.cron?x(s.cron):null;return{...s,nextRunAt:r?E(r):null}}function T(s,r){const t=r.name.trim();if(!t)return{ok:!1,error:"Name is required"};const c=R(r);if(!c.ok)return{ok:!1,error:c.error};const u=r.cron?.trim()||null;if(u&&!x(u))return{ok:!1,error:`Invalid cron expression: ${u}`};for(const d of r.nodes)if(d.kind==="session"&&!s.hookSessions?.getBySessionId(d.id))return{ok:!1,error:`Unknown session: ${d.id}`};const{entries:f}=S(r.nodes,r.edges),m=f.filter(d=>d.kind==="session");let l=r.projectId??null;if(m.length>0){const d=s.hookSessions.getBySessionId(m[0].id);if(l!=null&&l!==d.projectId)return{ok:!1,error:"projectId must match the entry sessions"};if(l=d.projectId,l==null)return{ok:!1,error:"Entry session has no project"};for(const h of m)if(s.hookSessions.getBySessionId(h.id).projectId!==l)return{ok:!1,error:"All entry sessions must belong to the same project"}}else{const d=r.nodes.find(h=>h.kind==="session");d&&(l=s.hookSessions.getBySessionId(d.id).projectId??l)}return l==null?{ok:!1,error:"projectId is required for webhook-only orchestrations"}:{ok:!0,value:{name:t,projectId:l,startText:(r.startText??"").trim(),nodes:r.nodes,edges:r.edges,cron:u}}}function M(s,r){for(const t of s.orchestrationRuns?.listRunning()??[])t.orchestrationId===r&&s.orchestrationEngine?.cancel(t.id)}export async function handleOrchestrationRoutes(s,r,t,c,u){if(c==="/messaging/orchestrations"){if(!t.orchestrations)return e(r,503,{error:"Messaging subsystem unavailable"}),!0;if(s.method==="GET"){const n=g(u,"projectId"),o=n===void 0?t.orchestrations.list():t.orchestrations.listByProject(n);return e(r,200,{orchestrations:o.map(I)}),!0}if(s.method==="POST"){let n;try{n=w.parse(await k(s))}catch(a){return e(r,400,{error:a instanceof Error?a.message:"Invalid body"}),!0}const o=T(t,n);return o.ok?(e(r,201,{ok:!0,orchestration:I(t.orchestrations.insert({...o.value,enabled:n.enabled}))}),!0):(e(r,400,{error:o.error}),!0)}}const f=c.match(/^\/messaging\/orchestrations\/(\d+)$/);if(f){const n=Number(f[1]);if(s.method==="PUT"){if(!t.orchestrations)return e(r,503,{error:"Messaging subsystem unavailable"}),!0;const o=t.orchestrations.getById(n);if(!o)return e(r,404,{error:"Orchestration not found"}),!0;let a;try{a=N.parse(await k(s))}catch(b){return e(r,400,{error:b instanceof Error?b.message:"Invalid body"}),!0}const p=T(t,{name:a.name??o.name,startText:a.startText??o.startText,projectId:a.projectId??(o.nodes.some(b=>b.kind==="session")?void 0:o.projectId),nodes:a.nodes??o.nodes,edges:a.edges??o.edges,cron:a.cron===void 0?o.cron:a.cron});return p.ok?(e(r,200,{ok:!0,orchestration:I(t.orchestrations.update(n,{...p.value,enabled:a.enabled}))}),!0):(e(r,400,{error:p.error}),!0)}if(s.method==="DELETE")return t.orchestrations?t.orchestrations.getById(n)?(M(t,n),t.orchestrations.deleteById(n),e(r,200,{ok:!0,orchestrationId:n}),!0):(e(r,404,{error:"Orchestration not found"}),!0):(e(r,503,{error:"Messaging subsystem unavailable"}),!0)}const m=c.match(/^\/messaging\/orchestrations\/(\d+)\/trigger$/);if(m&&s.method==="POST"){if(!t.orchestrationEngine||!t.orchestrations)return e(r,503,{error:"Messaging subsystem unavailable"}),!0;let n={};try{const a=(await v(s)).trim();a&&(n=P.parse(JSON.parse(a)))}catch{return e(r,400,{error:"Invalid body"}),!0}const o=await t.orchestrationEngine.start(Number(m[1]),"manual",n.text,n.entries);return o.ok?(e(r,201,{ok:!0,runId:o.runId}),!0):(e(r,o.status,{error:o.error}),!0)}const l=c.match(/^\/messaging\/orchestrations\/(\d+)\/rotate-webhook$/);if(l&&s.method==="POST"){if(!t.orchestrations)return e(r,503,{error:"Messaging subsystem unavailable"}),!0;let n;try{n=O.parse(await k(s))}catch(a){return e(r,400,{error:a instanceof Error?a.message:"Invalid body"}),!0}const o=t.orchestrations.rotateNodeToken(Number(l[1]),n.nodeId);return o?(e(r,200,{ok:!0,webhookToken:o}),!0):(e(r,404,{error:"Webhook entry node not found"}),!0)}const d=c.match(/^\/webhooks\/orchestrate\/([A-Za-z0-9_-]+)$/);if(d&&s.method==="POST"){if(!t.orchestrations||!t.orchestrationEngine)return e(r,503,{error:"Messaging subsystem unavailable"}),!0;const n=t.orchestrations.getByNodeToken(d[1]);if(!n)return e(r,404,{error:"Unknown webhook token"}),!0;const o=(await v(s)).trim().slice(0,2e4),a=await t.orchestrationEngine.start(n.row.id,"webhook",o||void 0,[n.nodeId]);return a.ok?(e(r,202,{ok:!0,runId:a.runId}),!0):(e(r,a.status,{error:a.error}),!0)}if(c==="/messaging/orchestration-runs"){if(!t.orchestrationRuns)return e(r,503,{error:"Messaging subsystem unavailable"}),!0;if(s.method==="GET"){const n=u.searchParams.get("status")||void 0;if(n&&!$.has(n))return e(r,400,{error:`Unknown run status: ${n}`}),!0;const o=t.orchestrationRuns.query({orchestrationId:g(u,"orchestrationId"),projectId:g(u,"projectId"),status:n,text:u.searchParams.get("text")||void 0,before:g(u,"before"),limit:g(u,"limit")});return e(r,200,{runs:o.runs.map(j),nextBefore:o.nextBefore}),!0}if(s.method==="DELETE"){const n=u.searchParams.get("scope")==="all"?"all":"finished",o=g(u,"projectId");if(n==="all")for(const a of t.orchestrationRuns.listRunning())o!=null&&a.projectId!==o||t.orchestrationEngine?.cancel(a.id);return e(r,200,{ok:!0,deleted:t.orchestrationRuns.clear(n,o)}),!0}}const h=c.match(/^\/messaging\/orchestration-runs\/(\d+)$/);if(h&&s.method==="GET"){if(!t.orchestrationRuns)return e(r,503,{error:"Messaging subsystem unavailable"}),!0;const n=t.orchestrationRuns.getById(Number(h[1]));return n?(e(r,200,{run:{...j(n),state:n.state}}),!0):(e(r,404,{error:"Run not found"}),!0)}const y=c.match(/^\/messaging\/orchestration-runs\/(\d+)\/cancel$/);if(y&&s.method==="POST"){if(!t.orchestrationRuns)return e(r,503,{error:"Messaging subsystem unavailable"}),!0;const n=t.orchestrationRuns.getById(Number(y[1]));return n?n.status!=="running"?(e(r,409,{error:`Run already ${n.status}`}),!0):(t.orchestrationEngine?.cancel(n.id)||t.orchestrationRuns.finish(n.id,"cancelled"),e(r,200,{ok:!0,runId:n.id}),!0):(e(r,404,{error:"Run not found"}),!0)}return!1}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{isHarness as I}from"@weavecode/core";import{readJson as
|
|
1
|
+
import{isHarness as I}from"@weavecode/core";import{readJson as P,sendJson as t}from"../http.js";import{messagingSurfaceFor as R}from"../../surfaces.js";import{projectFileIndex as b}from"../project-files.js";function k(r,e,s){if(!e.hookSessions||!e.hookEvents)return t(r,503,{error:"Hooks subsystem unavailable"}),null;const n=e.hookSessions.getBySessionId(s);return n?n.projectId==null?(t(r,400,{error:"Session is not bound to a project"}),null):e.projects.getById(n.projectId)||(t(r,404,{error:"Project not found"}),null):(t(r,404,{error:"Session not found"}),null)}function j(r,e){if(!r.hookEvents)return null;const s=r.hookEvents.listBySession(e,1),n=s[s.length-1]?.source;return I(n)?n:null}function y(r,e,s){const n=j(e,s),i=n?R(n):null;return(i?.pathRefs??null)||(t(r,409,{error:n?i?.unsupportedReasons?.pathRefs??`Harness "${n}" has no path reference syntax`:"Session has no hook events to determine its harness"}),null)}function S(r){if(r==null||r==="")return null;const e=Number(r);return Number.isInteger(e)&&e>0?e:null}function x(r,e){let s=0,n=r.length-1;for(;s<=n;){const i=s+n>>1,f=r[i];if(f===e)return!0;f<e?s=i+1:n=i-1}return!1}export async function handlePathRefRoutes(r,e,s,n,i){const f=n.match(/^\/sessions\/([^/]+)\/ref$/);if(f&&r.method==="GET"){const h=decodeURIComponent(f[1]);if(!k(e,s,h))return!0;const a=y(e,s,h);if(!a)return!0;const u=(i.searchParams.get("path")??"").replace(/^\/+|\/+$/g,"");if(!u)return t(e,400,{error:'Missing "path" query parameter'}),!0;const c=i.searchParams.get("kind")==="dir"?"dir":"file";if(!a.kinds.includes(c))return t(e,409,{error:`Harness does not accept "${c}" references`}),!0;const l=S(i.searchParams.get("start")),d=S(i.searchParams.get("end"));return a.lines?l==null?(t(e,200,{ref:a.expression({path:u,kind:c})}),!0):d!=null&&d<l?(t(e,400,{error:'"end" must not precede "start"'}),!0):(t(e,200,{ref:a.expression({path:u,kind:c,lines:{start:l,end:d??l}})}),!0):(t(e,200,{ref:a.expression({path:u,kind:c})}),!0)}const g=n.match(/^\/sessions\/([^/]+)\/refs\/recognize$/);if(g&&r.method==="POST"){const h=decodeURIComponent(g[1]),a=k(e,s,h);if(!a)return!0;const u=y(e,s,h);if(!u)return!0;let c="";try{const o=await P(r);c=typeof o?.text=="string"?o.text:""}catch{return t(e,400,{error:"Body must be JSON"}),!0}const l=await b(a.id,a.path),d=[];for(const o of u.recognize(c)){const p=o.kind==="dir"&&x(l.dirs,o.path)?"dir":x(l.files,o.path)?"file":null;if(!p||!u.kinds.includes(p))continue;const m=o.lines&&u.lines?o.lines:void 0;d.push({start:o.start,end:o.end,ref:u.expression({path:o.path,kind:p,...m?{lines:m}:{}}),path:o.path,kind:p,...m?{lines:m}:{}})}return t(e,200,{refs:d}),!0}return!1}
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
import type { IncomingMessage, ServerResponse } from 'node:http';
|
|
2
|
+
import type { WeaveServerDeps } from '../server.js';
|
|
3
|
+
export declare function handlePetRoutes(req: IncomingMessage, res: ServerResponse, _deps: WeaveServerDeps, pathname: string, _url: URL): Promise<boolean>;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import i from"node:path";import{createReadStream as w,promises as p}from"node:fs";import{PET_SPRITE_CONTRACT as j}from"@weavecode/core";import{sendJson as c}from"../http.js";import{getPetsDir as y}from"../../db/paths.js";import{isInsideDir as b}from"../../market/resolve.js";async function g(s){let t;try{t=await p.readFile(i.join(s,"pet.json"),"utf8")}catch{return null}let r;try{r=JSON.parse(t)}catch{return null}const n=typeof r.id=="string"?r.id:"";if(!n||n!==i.basename(s))return null;const[d,u,e]=await Promise.all([p.stat(i.join(s,"pet.json")).catch(()=>null),p.stat(i.join(s,"spritesheet.webp")).catch(()=>null),p.stat(i.join(s,"spritesheet.png")).catch(()=>null)]);return{id:n,displayName:typeof r.displayName=="string"?r.displayName:n,description:typeof r.description=="string"?r.description:"",spriteVersionNumber:typeof r.spriteVersionNumber=="number"?r.spriteVersionNumber:1,updatedAt:Math.floor(Math.max(d?.mtimeMs??0,u?.mtimeMs??0,e?.mtimeMs??0))}}export async function handlePetRoutes(s,t,r,n,d){if(!n.startsWith("/pets"))return!1;if(n==="/pets"&&s.method==="GET"){const e=y();let m;try{m=await p.readdir(e)}catch{return c(t,200,{pets:[],root:e}),!0}const a=(await Promise.all(m.map(o=>g(i.join(e,o))))).filter(o=>o!==null);return a.sort((o,l)=>o.id.localeCompare(l.id)),c(t,200,{pets:a,root:e}),!0}const u=n.match(/^\/pets\/([^/]+)\/spritesheet$/);if(u&&s.method==="GET"){const e=u[1];if(!/^[a-z0-9][a-z0-9-]{0,63}$/i.test(e))return c(t,400,{error:"Invalid pet id"}),!0;const m=y(),a=i.join(m,e);if(!b(a,m))return c(t,403,{error:"Pet path escapes the pets root"}),!0;if(!await g(a))return c(t,404,{error:`Pet "${e}" not found`}),!0;const o=i.join(a,"spritesheet.webp"),l=(await p.stat(o).catch(()=>null))?.isFile()?o:i.join(a,"spritesheet.png"),h=await p.stat(l).catch(()=>null);if(!h)return c(t,404,{error:`Pet "${e}" has no spritesheet`}),!0;if(h.size>j.maxSpritesheetBytes)return c(t,413,{error:"Spritesheet exceeds the size limit"}),!0;t.writeHead(200,{"content-type":l.endsWith(".png")?"image/png":"image/webp","content-length":String(h.size),"cache-control":"private, max-age=31536000, immutable"});const f=w(l);return f.on("error",()=>{typeof t.destroy=="function"&&t.destroy()}),f.pipe(t),!0}return!1}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{lstat as
|
|
1
|
+
import{lstat as v,readFile as F,stat as j}from"node:fs/promises";import P from"node:path";import{sendJson as n}from"../http.js";import{listDirOf as O,matchPaths as k,projectFileIndex as z}from"../project-files.js";import{resolveWithinProject as N}from"../../install/reader.js";const S=4*1024*1024,I=1024*1024,H=8192;function L(r){const t=Number(r);return!Number.isFinite(t)||t<=0?100:Math.min(200,Math.floor(t))}function $(r){switch(r.slice(r.lastIndexOf(".")+1).toLowerCase()){case"png":return"image/png";case"jpg":case"jpeg":return"image/jpeg";case"gif":return"image/gif";case"webp":return"image/webp";default:return null}}function B(r){switch(r.slice(r.lastIndexOf(".")+1).toLowerCase()){case"html":case"htm":return"text/html; charset=utf-8";case"svg":return"image/svg+xml";case"pdf":return"application/pdf";default:return null}}const M=new Set(["docx","doc","xlsx","xls","pptx","ppt","zip","gz","tar","rar","7z","exe","dll","bin","woff","woff2","ttf","otf","ico","mp4","mp3","wav","mov"]);function T(r){const t=r.slice(r.lastIndexOf(".")+1).toLowerCase();return M.has(t)?"application/octet-stream":null}export async function handleProjectFileRoutes(r,t,w,x,h){const y=x.match(/^\/projects\/(\d+)\/files$/);if(y&&r.method==="GET"){const s=w.projects.getById(Number(y[1]));if(!s)return n(t,404,{error:"Project not found"}),!0;const a=await z(s.id,s.path,{fresh:h.searchParams.get("fresh")==="1"}),p=h.searchParams.get("q")??"",c=(h.searchParams.get("dir")??"").replace(/^\/+|\/+$/g,""),d=L(h.searchParams.get("limit"));if(p.trim()){const{hits:e,total:i,capped:l}=await k(a,p,d,c);return n(t,200,{root:s.path,dir:c,total:i,capped:l,truncated:a.truncated,entries:e.map(o=>({path:o.path,name:o.path.slice(o.path.lastIndexOf("/")+1),kind:o.kind,ranges:o.ranges,...a.submodules[o.path]?{head:a.submodules[o.path]}:{}}))}),!0}const u=O(a,c),m=await Promise.all(u.slice(0,d).map(async e=>{const i={path:e.path,name:e.path.slice(e.path.lastIndexOf("/")+1),kind:e.kind,...e.head?{head:e.head}:{}},l=P.join(s.path,e.path),[o,f]=await Promise.all([v(l).catch(()=>null),e.kind==="file"?j(l).catch(()=>null):Promise.resolve(null)]),g=o?.isSymbolicLink()?{symlink:!0}:null;return f?{...i,...g,size:f.size,mtime:f.mtime.toISOString()}:g?{...i,...g}:i}));return n(t,200,{root:s.path,dir:c,total:u.length,capped:!1,truncated:a.truncated,entries:m}),!0}const b=x.match(/^\/projects\/(\d+)\/file$/);if(b&&r.method==="GET"){const s=w.projects.getById(Number(b[1]));if(!s)return n(t,404,{error:"Project not found"}),!0;const a=h.searchParams.get("path");if(!a)return n(t,400,{error:'Missing "path" query parameter'}),!0;let p;try{p=N(s.path,a)}catch{return n(t,403,{error:"Path escapes the project"}),!0}let c;try{c=await j(p)}catch{return n(t,404,{error:"File not found"}),!0}if(!c.isFile())return n(t,404,{error:"Not a file"}),!0;if(c.size>S)return n(t,413,{error:"File too large to preview"}),!0;const d=$(a),u=B(a),m=T(a);let e=await F(p);if(!d&&!u&&!m){if(e.subarray(0,H).includes(0))return n(t,415,{error:"Binary file"}),!0;if(e.length>I){const i=e.subarray(0,I),l=i.lastIndexOf(10);e=l>0?i.subarray(0,l):i,t.setHeader("x-weave-truncated","1")}}return u&&t.setHeader("content-security-policy","sandbox"),m&&t.setHeader("content-disposition",`attachment; filename*=UTF-8''${encodeURI(P.basename(a))}`),t.writeHead(200,{"content-type":d??u??m??"text/plain; charset=utf-8","content-length":String(e.length),"cache-control":"private, max-age=60"}),t.end(e),!0}return!1}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import
|
|
1
|
+
import g from"node:fs";import E from"node:path";import{isHarness as $}from"@weavecode/core";import{messagingSurfaceFor as J}from"../../surfaces.js";import{readBody as h,sendJson as o}from"../http.js";import{readDaemonSettings as j}from"../settings.js";import{closeTerminalsIn as A,defaultProjectOpener as u,readTerminalCounts as D,terminalBackendFor as R}from"../opener.js";import{purgeProjectPipeline as x}from"../hook-pipeline.js";import{hooksRoot as G}from"../../hooks/mirror.js";import{projectHarnesses as H,withProjectHarnesses as k}from"../project-harnesses.js";import{scheduleBootstrapInjection as C}from"../session-open.js";import{getUploadsDir as U}from"../../db/paths.js";export async function handleProjectRoutes(c,t,r,m){const w=m.match(/^\/projects\/(\d+)\/open$/);if(w&&c.method==="POST"){const e=r.projects.getById(Number(w[1]));if(!e)return o(t,404,{error:"Project not found"}),!0;let s;try{s=JSON.parse(await h(c))}catch{return o(t,400,{error:"Invalid JSON body"}),!0}if(s.target!=="explorer"&&s.target!=="terminal")return o(t,400,{error:'Invalid "target" (explorer|terminal)'}),!0;const n=r.opener??u;try{if(!(await g.promises.stat(e.path)).isDirectory())throw new Error(`Not a directory: ${e.path}`);if(s.target==="explorer")await n.openExplorer(e.path);else{const a=await j();await n.openTerminal(e.path,a.terminal),setTimeout(()=>{r.terminalRefresher?.refreshNow()},600)}o(t,200,{ok:!0,target:s.target,path:e.path})}catch(a){o(t,400,{error:a instanceof Error?a.message:"Open failed"})}return!0}const I=m.match(/^\/projects\/(\d+)\/close-terminal$/);if(I&&c.method==="POST"){const e=r.projects.getById(Number(I[1]));if(!e)return o(t,404,{error:"Project not found"}),!0;let s;try{s=JSON.parse(await h(c)||"{}")}catch{return o(t,400,{error:"Invalid JSON body"}),!0}if(!Array.isArray(s.paneIds)||s.paneIds.length===0||s.paneIds.some(i=>typeof i!="string"))return o(t,400,{error:"paneIds must be a non-empty array of strings"}),!0;const n=r.opener??u,a=await j();try{const i=await(n.closeTerminals??A)(e.path,a.terminal,s.paneIds);setTimeout(()=>{r.terminalRefresher?.refreshNow()},600),o(t,200,{ok:!0,closed:i})}catch(i){o(t,400,{error:i instanceof Error?i.message:"Close failed"})}return!0}const P=m.match(/^\/projects\/(\d+)\/focus-terminal$/);if(P&&c.method==="POST"){const e=r.projects.getById(Number(P[1]));if(!e)return o(t,404,{error:"Project not found"}),!0;let s;try{s=JSON.parse(await h(c)||"{}")}catch{return o(t,400,{error:"Invalid JSON body"}),!0}if(typeof s.targetId!="string"||!s.targetId)return o(t,400,{error:"targetId must be a non-empty string"}),!0;const n=r.opener??u,a=await j();try{await(n.focusTerminal??u.focusTerminal)(e.path,s.targetId,a.terminal),o(t,200,{ok:!0,targetId:s.targetId})}catch(i){o(t,409,{error:i instanceof Error?i.message:"Cannot focus terminal"})}return!0}const v=m.match(/^\/projects\/(\d+)\/new-session$/);if(v&&c.method==="POST"){const e=r.projects.getById(Number(v[1]));if(!e)return o(t,404,{error:"Project not found"}),!0;let s;try{s=JSON.parse(await h(c)||"{}")}catch{return o(t,400,{error:"Invalid JSON body"}),!0}const n=await H(e.path,r.harnesses);if(s.harness!==void 0&&!$(s.harness))return o(t,400,{error:'Invalid "harness"'}),!0;const a=s.harness;if(a&&!n.some(d=>d.id===a))return o(t,409,{error:`Harness "${a}" is not integrated in this project`}),!0;const i=a?[a]:n.map(d=>d.id),p=n.find(d=>i.includes(d.id)&&d.canStartSession),l=p?r.harnesses?.get(p.id)?.resume:void 0;if(!l?.bin)return o(t,501,{error:`Harness "${i[0]}" cannot start an interactive session`}),!0;const f=r.opener??u;try{if(!(await g.promises.stat(e.path)).isDirectory())throw new Error(`Not a directory: ${e.path}`);const d=await j(),O=[l.bin,...l.launchArgs??[]],y=await f.runInTerminal(e.path,O,d.terminal);y&&p&&J(p.id).paneEnvSource==="launch"&&r.messageDeliverer?.notePendingOrigin({harness:p.id,projectId:e.id,env:y.env}),y&&p&&l?.bootstrapText&&C(r,y,l.bootstrapText(e.name)),setTimeout(()=>{r.terminalRefresher?.refreshNow()},600),o(t,200,{ok:!0,command:O.join(" "),cwd:e.path})}catch(d){o(t,400,{error:d instanceof Error?d.message:"Open failed"})}return!0}if(m==="/projects"&&c.method==="GET")return o(t,200,{projects:await k(r.projects.list(),r.harnesses)}),!0;if(m==="/projects/archived"&&c.method==="GET")return o(t,200,{projects:await k(r.projects.listArchived(),r.harnesses)}),!0;const b=m.match(/^\/projects\/(\d+)\/archive$/);if(b&&c.method==="POST"){const e=r.projects.getById(Number(b[1]));if(!e)return o(t,404,{error:"Project not found"}),!0;if(e.archivedAt)return o(t,200,{project:e,purged:{events:0,dispatches:0,sessions:0,messages:0}}),!0;const s=r.hookDispatches?.deleteByProject(e.id)??0,n=r.hookEvents?.deleteByProject(e.id)??0;r.uploads?.pruneUnreferenced();const a=r.messageDeliverer?.forgetProject(e.id)??0;r.sessionWatches?.deleteByProject(e.id),r.orchestrations?.deleteByProject(e.id),r.orchestrationRuns?.clear("all",e.id),r.sideQuestions?.repo.deleteByProject(e.id);const i=r.hookSessions?.removeByProject(e.id)??0;return r.projects.setArchived(e.id,!0),x(r.hooksDir??G(),e.token),r.watch?.reconcile(),r.dataBus?.emit({key:"projects"}),o(t,200,{project:r.projects.getById(e.id),purged:{events:n,dispatches:s,sessions:i,messages:a}}),!0}const S=m.match(/^\/projects\/(\d+)\/restore$/);if(S&&c.method==="POST"){const e=r.projects.getById(Number(S[1]));return e?e.archivedAt?(r.projects.setArchived(e.id,!1),r.hookMirror?.syncProject(e.id),r.watch?.reconcile(),r.dataBus?.emit({key:"projects"}),o(t,200,{project:r.projects.getById(e.id)}),!0):(o(t,200,{project:e}),!0):(o(t,404,{error:"Project not found"}),!0)}if(m==="/projects/order"&&c.method==="PUT"){let e;try{e=JSON.parse(await h(c))}catch{return o(t,400,{error:"Invalid JSON body"}),!0}return!Array.isArray(e.ids)||!e.ids.every(s=>Number.isInteger(s))?(o(t,400,{error:'Invalid "ids" (integer array expected)'}),!0):(r.projects.setOrder(e.ids),r.dataBus?.emit({key:"projects"}),o(t,200,{projects:r.projects.list()}),!0)}const T=m.match(/^\/projects\/(\d+)\/panes$/);if(T&&c.method==="GET"){const e=r.projects.getById(Number(T[1]));if(!e)return o(t,404,{error:"Project not found"}),!0;const s=await j(),n=r.opener?.listPanes??u.listPanes;try{o(t,200,{projectId:e.id,panes:await n(e.path,s.terminal)})}catch(a){o(t,409,{error:a instanceof Error?a.message:"Cannot list panes"})}return!0}const N=m.match(/^\/projects\/(\d+)\/terminals$/);if(N&&c.method==="GET"){const e=r.projects.getById(Number(N[1]));if(!e)return o(t,404,{error:"Project not found"}),!0;const s=await j(),n=r.opener?.listTerminals??u.listTerminals,a=R(s.terminal).enumerable?await n(e.path,s.terminal):[];return o(t,200,{projectId:e.id,terminals:a}),!0}if(m==="/terminals/counts"&&c.method==="GET"){if(r.terminalRefresher)o(t,200,{counts:r.terminalRefresher.lastSnapshot?.counts??{}}),r.terminalRefresher.tick(!0);else{const e=r.opener??u;o(t,200,{counts:await D(r.projects.list(),e)})}return!0}const B=m.match(/^\/projects\/(\d+)\/storage$/);if(B){const e=r.projects.getById(Number(B[1]));if(!e)return o(t,404,{error:"Project not found"}),!0;const s=r.projects.getMeta(e.id)?.storage??{},n=r.uploads?.defaultDir??U();if(c.method==="GET")return o(t,200,{storage:s,effective:{images:s.images||n,files:s.files||n}}),!0;if(c.method==="PUT"){let a;try{a=JSON.parse(await h(c))}catch{return o(t,400,{error:"Invalid JSON body"}),!0}const i={};for(const p of["images","files"]){const l=a[p];if(l==null||l===""){i[p]=null;continue}if(typeof l!="string")return o(t,400,{error:`"${p}" must be a string or null`}),!0;const f=l.trim();if(!E.isAbsolute(f))return o(t,400,{error:`"${p}" must be an absolute path`}),!0;try{g.mkdirSync(f,{recursive:!0}),g.accessSync(f,g.constants.W_OK)}catch(d){return o(t,400,{error:`"${p}" is not writable: ${d instanceof Error?d.message:String(d)}`}),!0}i[p]=f}return r.projects.setMeta(e.id,{storage:i}),r.dataBus?.emit({key:"projects"}),o(t,200,{storage:i,effective:{images:i.images||n,files:i.files||n}}),!0}return!1}return!1}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{sendJson as
|
|
1
|
+
import{sendJson as c}from"../http.js";import{matchPaths as g,peekCachedIndex as v}from"../project-files.js";const j=8,m=12,k=6,f=18,y=1440*6e4,d=80;export async function handleSearchRoutes(e,o,t,a,r){if(a!=="/search"||e.method!=="GET")return!1;if(!t.hookEvents||!t.hookSessions)return c(o,503,{error:"Hooks subsystem unavailable"}),!0;const n=(r.searchParams.get("q")??"").trim();if(!n)return c(o,200,{q:n,sessions:[],messages:[],files:[],truncated:{messages:!1,files:!1}}),!0;const[u,h]=await Promise.all([t.hookSessions.searchByTitle(n,j),t.hookEvents.searchConversationTexts(n,m)]),I=t.projects.list().filter(s=>!s.archivedAt),l=(await Promise.all(I.map(async s=>{const p=await v(s.id,s.path,{maxStaleMs:y});if(!p)return[];const{hits:x}=await g(p,n,k,"");return x.map(i=>({projectId:s.id,path:i.path,kind:i.kind,ranges:i.ranges}))}))).flat().slice(0,f);return c(o,200,{q:n,sessions:u.map(s=>({sessionId:s.sessionId,projectId:s.projectId,title:s.title})),messages:h.map(s=>T(s,n)),files:l,truncated:{messages:h.length>=m,files:l.length>=f}}),!0}function T(e,o){const t=e.text.toLowerCase().indexOf(o.toLowerCase());if(t<0||e.text.length<=d*2)return{eventId:e.eventId,sessionId:e.sessionId,projectId:e.projectId,source:e.source,eventType:e.eventType,at:e.at,text:e.text,offset:Math.max(t,0),clipped:!1};const a=Math.max(0,t-d),r=Math.min(e.text.length,t+o.length+d);return{eventId:e.eventId,sessionId:e.sessionId,projectId:e.projectId,source:e.source,eventType:e.eventType,at:e.at,text:e.text.slice(a,r),offset:t-a,clipped:a>0||r<e.text.length}}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{z as
|
|
1
|
+
import{z as a}from"zod";import{readJson as d,sendJson as s}from"../http.js";import{composeAnswerAtoms as D}from"../../hooks/answer-keys.js";import{readSideQuestions as q}from"../../hooks/side-questions.js";const R=a.object({question:a.string().min(1).max(4e3)}),S=a.object({model:a.string().min(1).max(128)}),C=a.object({level:a.string().min(1).max(32)}),M=a.object({answers:a.array(a.object({questionKey:a.string().min(1),options:a.array(a.number().int().min(0)).max(32),text:a.string().max(2e3).optional()})).min(1)});export async function handleSessionControlRoutes(i,e,t,u,l){const g=u.match(/^\/sessions\/([^/]+)\/interrupt$/);if(g&&i.method==="POST"){if(!t.messageDeliverer)return s(e,503,{error:"Messaging subsystem unavailable"}),!0;const n=decodeURIComponent(g[1]),r=await t.messageDeliverer.interrupt(n);return r.ok?(setTimeout(()=>t.interruptRefresher?.tick(),1500),setTimeout(()=>t.interruptRefresher?.tick(),12e3),s(e,200,{ok:!0,sessionId:n,confirmed:r.confirmed}),!0):(s(e,r.status,{error:r.error}),!0)}const f=u.match(/^\/sessions\/([^/]+)\/close-pane$/);if(f&&i.method==="POST"){if(!t.messageDeliverer)return s(e,503,{error:"Messaging subsystem unavailable"}),!0;const n=decodeURIComponent(f[1]),r=await t.messageDeliverer.closePane(n);return r.ok?(setTimeout(()=>{t.livenessRefresher?.tick(),t.terminalRefresher?.refreshNow()},600),s(e,200,{ok:!0,sessionId:n}),!0):(s(e,r.status,{error:r.error}),!0)}const h=u.match(/^\/sessions\/([^/]+)\/mode$/);if(h&&i.method==="POST"){if(!t.messageDeliverer)return s(e,503,{error:"Messaging subsystem unavailable"}),!0;const n=decodeURIComponent(h[1]),r=await t.messageDeliverer.cycleMode(n);return r.ok?(s(e,200,{ok:!0,sessionId:n}),!0):(s(e,r.status,{error:r.error}),!0)}const p=u.match(/^\/sessions\/([^/]+)\/enter$/);if(p&&i.method==="POST"){if(!t.messageDeliverer)return s(e,503,{error:"Messaging subsystem unavailable"}),!0;const n=decodeURIComponent(p[1]),r=await t.messageDeliverer.pressEnter(n);return r.ok?(s(e,200,{ok:!0,sessionId:n}),!0):(s(e,r.status,{error:r.error}),!0)}const v=u.match(/^\/sessions\/([^/]+)\/ctrl-c$/);if(v&&i.method==="POST"){if(!t.messageDeliverer)return s(e,503,{error:"Messaging subsystem unavailable"}),!0;const n=decodeURIComponent(v[1]),r=await t.messageDeliverer.pressCtrlC(n);return r.ok?(s(e,200,{ok:!0,sessionId:n}),!0):(s(e,r.status,{error:r.error}),!0)}const b=u.match(/^\/sessions\/([^/]+)\/model$/);if(b&&i.method==="POST"){if(!t.messageDeliverer)return s(e,503,{error:"Messaging subsystem unavailable"}),!0;const n=decodeURIComponent(b[1]),r=S.parse(await d(i)),o=await t.messageDeliverer.setModel(n,r.model);return o.ok?(setTimeout(()=>t.interruptRefresher?.tick(),1500),s(e,200,{ok:!0,sessionId:n}),!0):(s(e,o.status,{error:o.error}),!0)}const k=u.match(/^\/sessions\/([^/]+)\/effort$/);if(k&&i.method==="POST"){if(!t.messageDeliverer)return s(e,503,{error:"Messaging subsystem unavailable"}),!0;const n=decodeURIComponent(k[1]),r=C.parse(await d(i)),o=await t.messageDeliverer.setEffort(n,r.level);return o.ok?(s(e,200,{ok:!0,sessionId:n}),!0):(s(e,o.status,{error:o.error}),!0)}if(u==="/messaging/questions"&&i.method==="GET")return t.questionTracker?(s(e,200,{questions:t.questionTracker.snapshot()}),!0):(s(e,503,{error:"Question tracking unavailable"}),!0);const I=u.match(/^\/sessions\/([^/]+)\/answer$/);if(I&&i.method==="POST"){if(!t.questionTracker||!t.messageDeliverer)return s(e,503,{error:"Question tracking unavailable"}),!0;const n=decodeURIComponent(I[1]);let r;try{r=M.parse(await d(i))}catch(y){return s(e,400,{error:y instanceof Error?y.message:"Invalid body"}),!0}const o=t.questionTracker.get(n);if(!o)return s(e,409,{error:"Session has no pending question"}),!0;const m=D(o.questions,r.answers);if(!m.ok)return s(e,400,{error:m.error}),!0;const c=await t.messageDeliverer.answer(n,m.atoms);return c.ok?(t.questionTracker.markAnswered(n),s(e,200,{ok:!0,sessionId:n}),!0):(s(e,c.status,{error:c.error}),!0)}const w=u.match(/^\/sessions\/([^/]+)\/side-question$/);if(w&&i.method==="POST"){if(!t.messageDeliverer||!t.sideQuestions)return s(e,503,{error:"Messaging subsystem unavailable"}),!0;const n=decodeURIComponent(w[1]);let r;try{r=R.parse(await d(i))}catch(c){return s(e,400,{error:c instanceof Error?c.message:"Invalid body"}),!0}const o=await t.messageDeliverer.askSideQuestion(n,r.question);if(!o.ok)return s(e,o.status,{error:o.error}),!0;const m=t.sideQuestions.repo.insert({sessionId:n,projectId:t.hookSessions?.getBySessionId(n)?.projectId??null,question:o.question});return s(e,200,{ok:!0,sideQuestion:m}),!0}const T=u.match(/^\/sessions\/([^/]+)\/side-questions$/);if(T&&i.method==="GET"){if(!t.sideQuestions)return s(e,503,{error:"Messaging subsystem unavailable"}),!0;const n=decodeURIComponent(T[1]),r=Number(l.searchParams.get("limit")),o=Number(l.searchParams.get("beforeId")),m=q(t.sideQuestions,n,{limit:Number.isFinite(r)&&r>0?Math.min(r,100):20,beforeId:Number.isFinite(o)&&o>0?o:void 0});return s(e,200,{sideQuestions:m}),!0}return!1}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{readFileSync as
|
|
1
|
+
import{readFileSync as A}from"node:fs";import j from"node:path";import{isHarness as T}from"@weavecode/core";import{sendJson as u}from"../http.js";import{blockingPromptFor as U,commandsSurfaceFor as $,editSurfaceFor as D,narrationSurfaceFor as J,rewindSurfaceFor as Q}from"../../surfaces.js";function k(o,n,t){if(!n.hookSessions||!n.hookEvents)return u(o,503,{error:"Hooks subsystem unavailable"}),null;const s=n.hookSessions.getBySessionId(t);return s?s.projectId==null?(u(o,400,{error:"Session is not bound to a project"}),null):n.projects.getById(s.projectId)||(u(o,404,{error:"Project not found"}),null):(u(o,404,{error:"Session not found"}),null)}function w(o,n){if(!o.hookEvents)return null;const t=o.hookEvents.listBySession(n,1),s=t[t.length-1]?.source;return T(s)?s:null}const B=20,q=2e3,z=200,F=new Map,W=2e5;function K(o){try{const n=JSON.parse(o);return[typeof n.toolName=="string"?n.toolName:null,n.toolInput??null,n.toolResponse??null]}catch{return[null,null,null]}}function M(o){if(!o)return null;try{const n=A(o,"utf8");return n.trim()?n:null}catch{return null}}const N=2e5,L=4e6;function V(o,n){const t=j.relative(n,o);return(t&&!t.startsWith("..")&&!j.isAbsolute(t)?t:o).split(j.sep).join("/")}function H(o){if(!o)return null;const n=Date.parse(o);return Number.isFinite(n)?n:null}function X(o,n,t){if(n===null&&t===null)return!0;if(!o)return!1;const s=Date.parse(o);return!(!Number.isFinite(s)||n!==null&&s<=n||t!==null&&s>t)}function Y(o,n){const t=[],s=new Map;let I=L,P=0,f=!1;for(const a of o){const d=a.hunk.before.slice(0,N),p=a.hunk.after.slice(0,N),b=d.length<a.hunk.before.length||p.length<a.hunk.after.length;b&&(f=!0);const E=d.length+p.length;if(E>I){f=!0;continue}I-=E;const e=V(a.path,n);let r=s.get(e);r||(r={path:e,hunks:[]},s.set(e,r),t.push(r)),r.hunks.push({before:d,after:p,at:a.at,...b?{clamped:!0}:{}}),P++}return{files:t,hunks:P,truncated:f}}export async function handleSessionInsightRoutes(o,n,t,s,I){const P=s.match(/^\/sessions\/([^/]+)\/plan$/);if(P&&o.method==="GET"){const e=decodeURIComponent(P[1]);if(!t.hookEvents)return u(n,503,{error:"Hook ingestion unavailable"}),!0;const r=t.hookEvents.listBySession(e,1),i=r[r.length-1]?.source,l=T(i)?U(i)?.plan??null:null;if(!l)return u(n,200,{plan:null}),!0;const h=c=>c.flatMap(v=>{const R=l.draftOf(...K(v.payload));return R?[{row:v,draft:R}]:[]}),m=r[r.length-1]?.id??0,S=t.hookEvents,y=F.get(e);if(y&&y.latestId===m)return u(n,200,{plan:y.plan}),!0;const x=c=>(F.size>=z&&F.clear(),F.set(e,{latestId:m,plan:c}),u(n,200,{plan:c}),!0),C=(c,v)=>{const R=S.listByTools(e,c,v,B,m-q);return R.length>0?R:S.listByTools(e,c,v,B)},[g]=h(C([l.tool],null));if(!g)return x(null);const[G]=h(C(l.writeTools,l.fileHint)).filter(c=>c.row.id<g.row.id),O=g.draft.text??M(g.draft.filePath)??G?.draft.text??M(G?.draft.filePath??null);return x(O?{eventId:g.row.id,at:g.row.createdAt,text:O.slice(0,W)}:null)}const f=s.match(/^\/sessions\/([^/]+)\/pre-question$/);if(f&&o.method==="GET"){const e=decodeURIComponent(f[1]);if(!k(n,t,e))return!0;const r=w(t,e),i=await(r?U(r):null)?.preQuestion?.(t.sessionProbe?.transcriptPathOf(e)??null);return u(n,200,{preQuestion:i??null}),!0}const a=s.match(/^\/sessions\/([^/]+)\/narration$/);if(a&&o.method==="GET"){const e=decodeURIComponent(a[1]);if(!k(n,t,e))return!0;const r=w(t,e),i=r?J(r):null;if(!i)return u(n,200,{supported:!1,narration:null}),!0;const l=await i.sessionNarration({sessionId:e,transcriptPath:t.sessionProbe?.transcriptPathOf(e)??null});return u(n,200,{supported:l!==null,narration:l}),!0}const d=s.match(/^\/sessions\/([^/]+)\/rewinds$/);if(d&&o.method==="GET"){const e=decodeURIComponent(d[1]);if(!k(n,t,e))return!0;const r=w(t,e),i=r?Q(r):null;if(!i)return u(n,200,{supported:!1,rewinds:null}),!0;const l=await i.sessionRewinds({sessionId:e,transcriptPath:t.sessionProbe?.transcriptPathOf(e)??null});return u(n,200,{supported:l!==null,rewinds:l}),!0}const p=s.match(/^\/sessions\/([^/]+)\/commands$/);if(p&&o.method==="GET"){const e=decodeURIComponent(p[1]),r=k(n,t,e);if(!r)return!0;const i=w(t,e),l=i?$(i):null;return l?(u(n,200,{supported:!0,commands:await l.list({projectPath:r.path}),inputModes:l.inputModes}),!0):(u(n,200,{supported:!1,commands:[],inputModes:[]}),!0)}const b=s.match(/^\/sessions\/([^/]+)\/command-executions$/);if(b&&o.method==="GET"){const e=decodeURIComponent(b[1]);if(!k(n,t,e))return!0;const r=w(t,e),i=r?$(r):null;if(!i)return u(n,200,{supported:!1,executions:null}),!0;const l=await i.executions(t.sessionProbe?.transcriptPathOf(e)??null);return u(n,200,{supported:l!==null,executions:l}),!0}const E=s.match(/^\/sessions\/([^/]+)\/edits$/);if(E&&o.method==="GET"){const e=decodeURIComponent(E[1]),r=k(n,t,e);if(!r)return!0;const i=w(t,e),l=i?D(i):null;if(!l)return u(n,200,{files:null,hunks:0,truncated:!1,reason:"unsupported"}),!0;const h=await l.sessionEdits({sessionId:e,transcriptPath:t.sessionProbe?.transcriptPathOf(e)??null});if(!h)return u(n,200,{files:null,hunks:0,truncated:!1,reason:"unreadable"}),!0;const m=H(I.searchParams.get("since")),S=H(I.searchParams.get("until")),y=m!==null||S!==null?h.filter(x=>X(x.at,m,S)):h;return u(n,200,Y(y,r.path)),!0}return!1}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{readBody as
|
|
1
|
+
import{readBody as u,sendJson as s}from"../http.js";import{DEFAULT_AI_SETTINGS as b,DEFAULT_DECISION_SETTINGS as E,readDaemonSettings as f,writeDaemonSettings as T,terminalPresetsFor as K}from"../settings.js";import{readAiKey as N,writeAiKey as G}from"../ai-config.js";import{readDecisionKey as U,writeDecisionKey as I}from"../decision-config.js";import{accessUrls as j}from"../tls.js";import{applyLaunchOnLogin as A}from"../auto-start.js";import{closePetWindow as O,openPetWindow as v}from"../pet-window.js";import{WEAVE_VERSION as C}from"../../version.js";import{readProjectConfig as h,writeProjectConfig as D}from"../../install/project-config.js";import{readStatuslineConfig as y,readStatuslineScript as J,readStatuslineFacts as F,applyStatuslineConfig as g,readGlobalStatuslineConfig as S,writeGlobalStatuslineConfig as B}from"../../statusline/manager.js";import{DEFAULT_STATUSLINE_CONFIG as L}from"../../statusline/config.js";import{listBrowseRoots as _,listDirectoryChildren as k}from"../fs-browser.js";import{projectFileNamespaces as W}from"../../hooks/toolkit.js";import{listGlobalFileAssets as $}from"../../install/global-file-assets.js";function w(o,r,e){const c=o.ai??b,p=o.decision??E,d=N(r),m=U(e);return{...o,ai:{baseUrl:c.baseUrl,model:c.model,apiKey:d,apiKeySet:d!==null},decision:{baseUrl:p.baseUrl,model:p.model,apiKey:m,apiKeySet:m!==null}}}function P(o){if(!o)return;const{apiKey:r,...e}=o;return e}export async function handleSettingsRoutes(o,r,e,c,p){if(c==="/settings"){if(o.method==="GET")return s(r,200,{settings:w(await f(),e.aiKeyPath,e.decisionKeyPath),presets:K(process.platform),platform:process.platform,urls:j(e.port,e.tlsPort??0),version:C,repoUrl:"https://github.com/zijing66/weave"}),!0;if(o.method==="PUT"){let t;try{t=JSON.parse(await u(o))}catch{return s(r,400,{error:"Invalid JSON body"}),!0}const a=t.ai?.apiKey;a!==void 0&&G(typeof a=="string"?a:null,e.aiKeyPath);const i=t.decision?.apiKey;i!==void 0&&I(typeof i=="string"?i:null,e.decisionKeyPath);const n=await f(),l=await T({...n,...t,ai:t.ai?P(t.ai):n.ai,decision:t.decision?P(t.decision):n.decision,pet:t.pet?{...n.pet,...t.pet}:n.pet});return e.hookEvents?.resetPrune(),(e.autoStart??A)(l.startup?.launchOnLogin??!1),l.pet?.enabled?v({baseUrl:`http://localhost:${e.port}`,auth:e.auth??null}):O(),e.dataBus?.emit({key:"settings"}),s(r,200,w(l,e.aiKeyPath,e.decisionKeyPath)),!0}}if(c==="/fs/roots"&&o.method==="GET"){const t=e.libraries?e.libraries.list().map(i=>i.path):[],a=await _(t);return s(r,200,{roots:a}),!0}if(c==="/fs/children"&&o.method==="GET"){const t=p.searchParams.get("path");if(!t)return s(r,400,{error:'Missing "path" query parameter'}),!0;try{const a=await k(t);s(r,200,{children:a})}catch(a){s(r,400,{error:`Cannot list directory: ${String(a)}`})}return!0}const d=c.match(/^\/projects\/(\d+)\/config$/);if(d){const t=e.projects.getById(Number(d[1]));if(!t)return s(r,404,{error:"Project not found"}),!0;if(o.method==="GET")return s(r,200,await h(t.path)),!0;if(o.method==="PUT"){let a;try{a=JSON.parse(await u(o))}catch{return s(r,400,{error:"Invalid JSON body"}),!0}const i=await h(t.path),n={lastSyncAt:a.lastSyncAt??i.lastSyncAt};return await D(t.path,n),s(r,200,n),!0}}if(c==="/statusline/global"){if(o.method==="GET")return s(r,200,{config:await S()}),!0;if(o.method==="PUT"){let t;try{t=JSON.parse(await u(o))}catch{return s(r,400,{error:"Invalid JSON body"}),!0}try{await B(t);for(const a of e.projects.list()){const i=await y(a.path);i.source==="global"&&await g(a.path,i)}e.dataBus?.emit({key:"statusline"}),s(r,200,{ok:!0})}catch(a){s(r,400,{error:a instanceof Error?a.message:"Global statusline update failed"})}return!0}}if(c==="/statusline/default"&&o.method==="GET")return s(r,200,{config:L}),!0;const m=c.match(/^\/projects\/(\d+)\/statusline$/);if(m){const t=e.projects.getById(Number(m[1]));if(!t)return s(r,404,{error:"Project not found"}),!0;if(o.method==="GET"){const[a,i,n]=await Promise.all([y(t.path),J(t.path),S()]);return s(r,200,{config:a,script:i,globalConfig:n,facts:F(t.path)}),!0}if(o.method==="PUT"){let a;try{a=JSON.parse(await u(o))}catch{return s(r,400,{error:"Invalid JSON body"}),!0}try{await g(t.path,a),e.dataBus?.emit({key:"statusline",projectPath:t.path}),s(r,200,{ok:!0})}catch(i){s(r,400,{error:i instanceof Error?i.message:"Statusline update failed"})}return!0}}if(c==="/assets"&&o.method==="GET"){const t=p.searchParams.get("path");if(!t)return s(r,400,{error:'Missing "path" query parameter'}),!0;if(!e.watch)return s(r,503,{error:"Watch service unavailable"}),!0;const a=await W(t),i=e.watch.getAssets(t).map(n=>{const l=a.get(n.relPath);return l?{...n,namespace:l}:n});return s(r,200,{projectPath:t,assets:i}),!0}return c==="/global-file-assets"&&o.method==="GET"?(s(r,200,{assets:await $()}),!0):!1}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{createReadStream as
|
|
1
|
+
import{createReadStream as w}from"node:fs";import{z as u}from"zod";import{readJson as c,readRawBody as E,sendJson as a}from"../http.js";import{isImageMediaType as I,maxUploadBytes as b}from"../../repositories/uploads.js";import{defaultUploadSessions as S}from"../upload-sessions.js";const z=u.object({name:u.string().min(1).max(200),mediaType:u.string().min(1).max(100),data:u.string().min(1),projectId:u.number().int().positive().optional()}),B=u.object({name:u.string().min(1).max(200),mediaType:u.string().min(1).max(100),size:u.number().int().positive(),projectId:u.number().int().positive().optional()});function j(n,e){return(I(e)?n?.images:n?.files)??null}const x=16*1024*1024;function f(n,e){return{id:e.id,name:e.name,mediaType:e.mediaType,size:e.size,path:n.uploads.pathOf(e)}}function g(n,e,t){if(!n.projects.getById(e))return null;const d=n.projects.getMeta(e);return j(d?.storage,t)}export async function handleUploadRoutes(n,e,t,d,h){const l=t.uploadSessions??S;if(d==="/uploads/begin"&&n.method==="POST"){if(!t.uploads)return a(e,503,{error:"Upload subsystem unavailable"}),!0;let r;try{r=B.parse(await c(n))}catch(i){return a(e,400,{error:i instanceof Error?i.message:"Invalid body"}),!0}if(r.size>b(r.mediaType))return a(e,413,{error:"File too large"}),!0;const o=r.projectId?g(t,r.projectId,r.mediaType):null,s=await l.begin({...r,dir:o});return a(e,201,{uploadId:s.id,received:0,size:s.size}),!0}const m=d.match(/^\/uploads\/([0-9a-f-]{36})\/finish$/);if(m&&n.method==="POST"){if(!t.uploads)return a(e,503,{error:"Upload subsystem unavailable"}),!0;const r=await l.finish(m[1]);if(!r)return a(e,409,{error:"Upload incomplete"}),!0;const o=await t.uploads.adoptFromFile(r);return await l.abort(m[1]),a(e,201,{upload:f(t,o)}),!0}const y=d.match(/^\/uploads\/([0-9a-f-]{36})$/);if(y){const r=y[1];if(n.method==="GET"){const o=await l.get(r);return o?(a(e,200,{received:o.received,size:o.size,name:o.name,mediaType:o.mediaType}),!0):(a(e,404,{error:"Upload not found"}),!0)}if(n.method==="PUT"){const o=Number(h.searchParams.get("offset")??"");if(!Number.isInteger(o)||o<0)return a(e,400,{error:"Invalid offset"}),!0;const s=await E(n,x).catch(()=>null);if(!s)return a(e,413,{error:"Chunk too large"}),!0;const i=await l.append(r,o,s);return i.kind==="missing"?(a(e,404,{error:"Upload not found"}),!0):i.kind==="conflict"?(a(e,409,{received:i.received}),!0):i.kind==="overflow"?(a(e,413,{received:i.received,error:"Exceeds declared size"}),!0):(a(e,200,{received:i.received}),!0)}if(n.method==="DELETE")return await l.abort(r),a(e,200,{ok:!0}),!0}if(d==="/uploads"&&n.method==="POST"){if(!t.uploads)return a(e,503,{error:"Upload subsystem unavailable"}),!0;let r;try{r=z.parse(await c(n))}catch(i){return a(e,400,{error:i instanceof Error?i.message:"Invalid body"}),!0}const o=Buffer.from(r.data,"base64");if(o.length===0)return a(e,400,{error:"Empty upload"}),!0;if(o.length>b(r.mediaType))return a(e,413,{error:"File too large"}),!0;const s=t.uploads.save({name:r.name,mediaType:r.mediaType,bytes:o,dir:r.projectId?g(t,r.projectId,r.mediaType):null});return a(e,201,{upload:f(t,s)}),!0}const p=d.match(/^\/sessions\/([^/]+)\/uploads$/);if(p&&n.method==="GET"){if(!t.uploads)return a(e,503,{error:"Upload subsystem unavailable"}),!0;const r=t.uploads.uploadsBySession(decodeURIComponent(p[1]));return a(e,200,{uploads:(r??[]).map(o=>({...f(t,o),createdAt:o.createdAt})),totalBytes:(r??[]).reduce((o,s)=>o+s.size,0)}),!0}if(p&&n.method==="DELETE"){if(!t.uploads)return a(e,503,{error:"Upload subsystem unavailable"}),!0;const r=t.uploads.uploadsBySession(decodeURIComponent(p[1]));if(!r)return a(e,200,{removed:0,freedBytes:0}),!0;const o=r.reduce((i,U)=>i+U.size,0),s=t.uploads.removeMany(r.map(i=>i.id));return t.dataBus?.emit({key:"sessions"}),a(e,200,{removed:s,freedBytes:o}),!0}if(d==="/uploads/unreferenced"&&n.method==="GET")return t.uploads?(a(e,200,t.uploads.unreferencedStats()),!0):(a(e,503,{error:"Upload subsystem unavailable"}),!0);if(d==="/uploads/overview"&&n.method==="GET")return t.uploads?(a(e,200,t.uploads.overview()),!0):(a(e,503,{error:"Upload subsystem unavailable"}),!0);const T=u.object({ids:u.array(u.string().regex(/^[a-f0-9]{64}$/)).min(1).max(500)});if(d==="/uploads/remove"&&n.method==="POST"){if(!t.uploads)return a(e,503,{error:"Upload subsystem unavailable"}),!0;let r;try{r=T.parse(await c(n))}catch(s){return a(e,400,{error:s instanceof Error?s.message:"Invalid body"}),!0}const o=t.uploads.removeMany(r.ids);return t.dataBus?.emit({key:"sessions"}),a(e,200,{removed:o}),!0}if(d==="/uploads/usage"&&n.method==="GET")return t.uploads?(a(e,200,{sessions:t.uploads.usageBySession()}),!0):(a(e,503,{error:"Upload subsystem unavailable"}),!0);if(d==="/uploads/unreferenced"&&n.method==="POST"){if(!t.uploads)return a(e,503,{error:"Upload subsystem unavailable"}),!0;let r={done:0,total:0};const o=t.uploads.cleanupUnreferenced((s,i)=>{r={done:s,total:i}});return t.dataBus?.emit({key:"sessions"}),a(e,200,{removed:o,...r}),!0}const v=d.match(/^\/images\/([a-f0-9]{64})$/);if(v&&n.method==="GET"){if(!t.uploads)return a(e,503,{error:"Upload subsystem unavailable"}),!0;const r=t.uploads.fileStatOf(v[1]);if(!r)return a(e,404,{error:"Image not found"}),!0;e.writeHead(200,{"content-type":r.row.mediaType,"content-length":String(r.size),"cache-control":"private, max-age=31536000, immutable"});const o=w(r.file);return o.on("error",()=>{typeof e.destroy=="function"&&e.destroy()}),o.pipe(e),!0}return!1}
|
|
@@ -1 +1,2 @@
|
|
|
1
|
-
import
|
|
1
|
+
import c from"node:path";import D from"node:os";import{promises as u}from"node:fs";import{HARNESS_DIRS as w,VISUALIZATION_PROTOCOL as m}from"@weavecode/core";import{sendJson as f}from"../http.js";import{isInsideDir as L}from"../../market/resolve.js";import{getVisualizationsDir as N}from"../../db/paths.js";function y(r){return r.visualizationsDir??N()}function O(r){const e=D.homedir(),i=[c.join(e,w.codex.userDir,"visualizations"),c.join(e,w.claude.userDir),c.join(e,w.codex.userDir,"plugins"),c.join(D.tmpdir(),"weave"),y(r)];for(const n of r.projects.list())i.push(n.path);return i}const F=1440*60*1e3,T=[m.referencePrefix,...m.referencePrefixAliases],A=[m.referenceSuffix,...m.referenceSuffixAliases];function P(r){const e=[];for(const i of r.split(`
|
|
2
|
+
`)){const n=i.trim(),a=T.find(o=>n.startsWith(o));if(!a)continue;let t=n.slice(a.length);const s=A.find(o=>t.endsWith(o));s&&(t=t.slice(0,-s.length));try{const o=JSON.parse(t);typeof o.path=="string"&&o.path&&e.push(c.resolve(o.path))}catch{}}return e}function M(r){const e=new Set;for(const i of r.hookEvents?.conversationTextsContaining("visualize")??[])for(const n of P(i))e.add(n.toLowerCase());return e}async function S(r){const e=[],i=async n=>{let a;try{a=await u.readdir(n,{withFileTypes:!0})}catch{return}for(const t of a){const s=c.join(n,t.name);if(t.isDirectory()){await i(s);continue}if(!(!t.isFile()||c.extname(t.name).toLowerCase()!==".html"))try{const o=await u.stat(s);e.push({file:s,size:o.size,mtimeMs:o.mtimeMs})}catch{}}};return await i(r),e}async function I(r){const e=y(r),i=await S(e),n=M(r),a=Date.now()-F,t={root:e,count:i.length,bytes:0,unreferenced:{count:0,bytes:0}};for(const s of i)t.bytes+=s.size,!(n.has(s.file.toLowerCase())||s.mtimeMs>a)&&(t.unreferenced.count+=1,t.unreferenced.bytes+=s.size);return t}export async function handleVisualizationRoutes(r,e,i,n,a){if(n==="/visualizations/stats"&&r.method==="GET")return f(e,200,await I(i)),!0;if(n==="/visualizations/cleanup"&&r.method==="POST"){const p=await S(y(i)),j=M(i),C=Date.now()-F;let v=0,x=0;for(const h of p)if(!(j.has(h.file.toLowerCase())||h.mtimeMs>C))try{await u.unlink(h.file),v+=1,x+=h.size}catch{}return f(e,200,{removed:v,freedBytes:x}),!0}if(n!=="/visualizations/fragment"||r.method!=="GET")return!1;const t=a.searchParams.get("path")??"",s=c.resolve(t);if(!t||!c.isAbsolute(t))return f(e,400,{error:'Missing or relative "path" query parameter'}),!0;const o=O(i);if(!o.some(p=>L(s,p)))return f(e,403,{error:`Fragment path is outside the allowed roots: ${o.join(", ")}`}),!0;if(c.extname(s).toLowerCase()!==".html")return f(e,403,{error:"Only .html fragments are served"}),!0;let l;try{l=await u.stat(s)}catch{return f(e,404,{error:"Fragment file not found"}),!0}if(!l.isFile())return f(e,404,{error:"Fragment path is not a file"}),!0;e.setHeader("cache-control","no-store");const d=Math.floor(l.mtimeMs),g=a.searchParams.get("mtime"),z=g==null?NaN:Number(g);if(Number.isFinite(z)&&z===d)return f(e,200,{unchanged:!0,mtimeMs:d}),!0;if(l.size>m.maxFragmentBytes)return f(e,413,{error:"Fragment exceeds the 1 MB size limit"}),!0;const b=await u.readFile(s,"utf8");return f(e,200,{html:b,mtimeMs:d}),!0}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
import{z as
|
|
1
|
+
import{z as t}from"zod";import{isHarness as I}from"@weavecode/core";import{readJson as m,sendJson as s}from"../http.js";import{messagingSurfaceFor as v}from"../../surfaces.js";import{DEFAULT_WATCH_ON as E}from"../../repositories/session-watches.js";const k=t.object({watcherSessionId:t.string().min(1).nullable().optional(),notify:t.string().min(1).max(2e4).nullable().optional(),on:t.array(t.enum(["idle","turnEnd","messageFailed"])).min(1).optional(),times:t.number().int().min(1).max(100).nullable().optional()}),W=t.object({watchId:t.number().int().positive()}),T=t.object({endpoint:t.string().url(),keys:t.object({p256dh:t.string().min(1),auth:t.string().min(1)})}),B=t.object({endpoint:t.string().url()});function P(i,e){return i.queuedPrompt!==null||i.prompt!==null||e}export async function handleWatchRoutes(i,e,n,l){const f=l.match(/^\/sessions\/([^/]+)\/watch$/);if(f){const r=decodeURIComponent(f[1]);if(i.method==="POST"){if(!n.sessionWatches||!n.hookSessions||!n.hookEvents)return s(e,503,{error:"Messaging subsystem unavailable"}),!0;let o;try{o=k.parse(await m(i))}catch(u){return s(e,400,{error:u instanceof Error?u.message:"Invalid body"}),!0}if(!n.hookSessions.getBySessionId(r))return s(e,404,{error:"Session not found"}),!0;const c=n.hookEvents.listBySession(r,1),a=c[c.length-1]?.source;if(!I(a))return s(e,400,{error:"Session has no hook events to determine its harness"}),!0;const d=v(a),h=o.on??[...E];if((h.includes("idle")||h.includes("turnEnd"))&&d.idleSignals.length===0)return s(e,409,{error:d.unsupportedReasons?.watch??`Harness "${a}" does not support idle watching`}),!0;if(h.includes("messageFailed")&&!(P(d,n.messageDeliverer?.hasTerminalChannel()??!1)||d.inject!==null||d.headless!==null))return s(e,409,{error:d.unsupportedReasons?.prompt??`Harness "${a}" supports no messaging channel`}),!0;if(o.watcherSessionId){if(!n.hookSessions.getBySessionId(o.watcherSessionId))return s(e,404,{error:"Watcher session not found"}),!0;const u=n.hookEvents.listBySession(o.watcherSessionId,1),g=u[u.length-1]?.source;if(!I(g))return s(e,400,{error:"Watcher session has no hook events to determine its harness"}),!0;const w=v(g);if(!w.inject)return s(e,409,{error:w.unsupportedReasons?.inject??`Harness "${g}" cannot receive watch notifications`}),!0}const b=o.times===void 0?1:o.times,y=(o.watcherSessionId??null)===null?n.sessionWatches.listPendingByTarget(r).find(u=>u.watcherSessionId===null):void 0,S=y?n.sessionWatches.updateById(y.id,{onEvents:h,remaining:b}):void 0,p=S??n.sessionWatches.insert({watcherSessionId:o.watcherSessionId??null,targetSessionId:r,notify:o.notify??null,onEvents:h,times:b});return n.watchEngine?.created(p),s(e,S?200:201,{ok:!0,watchId:p.id,watch:p}),!0}if(i.method==="DELETE"){if(!n.sessionWatches)return s(e,503,{error:"Messaging subsystem unavailable"}),!0;let o;try{o=W.parse(await m(i))}catch(a){return s(e,400,{error:a instanceof Error?a.message:"Invalid body"}),!0}const c=n.sessionWatches.getById(o.watchId);return!c||c.targetSessionId!==r||c.firedAt!==null?(s(e,404,{error:"Watch not found"}),!0):(n.sessionWatches.deleteById(o.watchId),s(e,200,{ok:!0,watchId:o.watchId}),!0)}}if(l==="/messaging/watches"&&i.method==="GET")return n.sessionWatches?(s(e,200,{watches:n.sessionWatches.listPending()}),!0):(s(e,503,{error:"Messaging subsystem unavailable"}),!0);if(l==="/messaging/push/key"&&i.method==="GET")return n.pushNotifier?(s(e,200,{publicKey:n.pushNotifier.publicKey()}),!0):(s(e,503,{error:"Push subsystem unavailable"}),!0);if(l==="/messaging/push/subscribe"&&i.method==="POST"){if(!n.pushSubscriptions)return s(e,503,{error:"Push subsystem unavailable"}),!0;try{const r=T.parse(await m(i)),o=n.pushSubscriptions.upsert({endpoint:r.endpoint,p256dh:r.keys.p256dh,auth:r.keys.auth,userAgent:i.headers["user-agent"]??null});s(e,201,{ok:!0,subscription:o})}catch(r){s(e,400,{error:r instanceof Error?r.message:"Invalid body"})}return!0}if(l==="/messaging/push/unsubscribe"&&i.method==="POST"){if(!n.pushSubscriptions)return s(e,503,{error:"Push subsystem unavailable"}),!0;try{const r=B.parse(await m(i));n.pushSubscriptions.deleteByEndpoint(r.endpoint),s(e,200,{ok:!0})}catch(r){s(e,400,{error:r instanceof Error?r.message:"Invalid body"})}return!0}return!1}
|
|
@@ -46,6 +46,10 @@ export interface WeaveServerDeps {
|
|
|
46
46
|
watch?: WatchService;
|
|
47
47
|
/** Hook event repository; optional so non-ingestion tests can omit it. */
|
|
48
48
|
hookEvents?: HookEventRepository;
|
|
49
|
+
/** 渲染块 fragment 落点根;缺省 `<data>/visualizations`(测试注入临时目录)。 */
|
|
50
|
+
visualizationsDir?: string;
|
|
51
|
+
/** 本机停机入口(`POST /daemon/shutdown`):走 start.ts 的 shutdown 链,先并 WAL 再退。 */
|
|
52
|
+
requestShutdown?: () => void;
|
|
49
53
|
/**
|
|
50
54
|
* 事件接入源(批 4b:类型由 HookAdapter 放宽为结构兼容的 EventSource,
|
|
51
55
|
* `HookAdapter[]` 仍可赋值);`harnesses` 存在时 POST /hooks 由其派生。
|