aws-runtime-bridge 1.9.189 → 1.9.192
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/CHANGELOG.md +111 -0
- package/dist/adapter/AcodeSdkAdapter.d.ts +13 -0
- package/dist/adapter/AcodeSdkAdapter.js +3 -3
- package/dist/config.d.ts +0 -31
- package/dist/config.js +2 -2
- package/dist/index.js +1 -1
- package/dist/routes/media-files.d.ts +19 -0
- package/dist/routes/media-files.js +2 -0
- package/dist/routes/plugin-ui.d.ts +17 -0
- package/dist/routes/plugin-ui.js +2 -0
- package/dist/routes/plugins.d.ts +3 -0
- package/dist/routes/plugins.js +1 -1
- package/dist/routes/terminal.d.ts +83 -0
- package/dist/routes/terminal.js +25 -25
- package/dist/scripts/migrate-user-scopes.js +1 -1
- package/dist/services/agent-capability-sync.js +1 -1
- package/dist/services/capability-config.d.ts +0 -1
- package/dist/services/capability-config.js +2 -2
- package/dist/services/instance-ai-config-service.js +1 -1
- package/dist/services/plugin-deployment.d.ts +2 -30
- package/dist/services/plugin-deployment.js +2 -2
- package/dist/services/plugin-handler-adapter.d.ts +10 -1
- package/dist/services/plugin-handler-adapter.js +2 -2
- package/dist/services/plugin-listener-runner.js +4 -4
- package/dist/services/plugin-loader.d.ts +7 -1
- package/dist/services/plugin-loader.js +1 -1
- package/dist/services/plugin-manager.d.ts +32 -12
- package/dist/services/plugin-manager.js +4 -4
- package/dist/services/plugin-manifest.d.ts +53 -3
- package/dist/services/plugin-manifest.js +1 -1
- package/dist/services/plugin-runtime.d.ts +8 -9
- package/dist/services/plugin-ui-status-runtime.d.ts +8 -0
- package/dist/services/plugin-ui-status-runtime.js +2 -0
- package/dist/services/plugin-ui-status.d.ts +96 -0
- package/dist/services/plugin-ui-status.js +2 -0
- package/dist/services/plugin-wecom-callback.d.ts +61 -0
- package/dist/services/plugin-wecom-callback.js +3 -0
- package/dist/services/user-scope.d.ts +1 -9
- package/dist/services/user-scope.js +1 -1
- package/package/acode/dist/plugin-types.d.ts +41 -1
- package/package/acode/dist/runtime.d.ts +17 -0
- package/package/acode/dist/runtime.js +20 -20
- package/package/aws-client-agent-mcp/dist/mcp-server.js +1 -1
- package/package/aws-client-agent-mcp/dist/mcp-tools.d.ts +15 -0
- package/package/aws-client-agent-mcp/dist/mcp-tools.js +35 -5
- package/package/aws-client-agent-mcp/dist/tool-groups.js +2 -2
- package/package.json +1 -1
package/dist/config.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import a from"node:fs";import
|
|
1
|
+
import a from"node:fs";import L from"node:net";import{homedir as C}from"node:os";import n from"node:path";import{fileURLToPath as N}from"node:url";import{logger as h}from"./utils/logger.js";function H(e){return String(e??"").replace(/[^a-zA-Z0-9_.-]/g,"_").replace(/^\.+/g,"")}function v(){return String(process.env.AWS_RUNTIME_ENV||"").trim().toLowerCase()==="development"}function Z(){return String(process.env.AWS_BRIDGE_APP_MODE||"").trim().toLowerCase()==="desktop"}function Q(){return String(process.env.AWS_BRIDGE_SHELL_TOKEN||"").trim()}function B(){return String(process.env.AWS_BRIDGE_LISTEN_HOST||"").trim()||void 0}let E;function M(){if(E!==void 0)return E;const e=n.dirname(N(import.meta.url)),r=n.resolve(e,".."),t=n.resolve(r,".."),o=a.existsSync(n.join(t,".git"))||a.existsSync(n.join(t,"package.json"));return E=n.join(o?t:r,".dev-home"),E}function U(){return String(process.env.AWS_TEST_HOME||"").trim()||String(process.env.AWS_RUNTIME_HOME_DIR||"").trim()||C()}function R(){return v()?String(process.env.AWS_TEST_HOME||"").trim()||String(process.env.AWS_RUNTIME_HOME_DIR||"").trim()||M():U()}const W=18081,w=28081,x=Number(process.env.AWS_RUNTIME_BRIDGE_PORT||(v()?w:W));let m;function j(){return m??x}function k(e){m=e}function ee(){m=void 0}function T(e){return new Promise(r=>{const t=L.createServer();t.once("error",o=>{const s=o.code==="EADDRINUSE"||o.code==="EACCES"||o.code==="EPERM";r(!s)}),t.once("listening",()=>{t.close(()=>r(!0))}),t.listen(e)})}async function D(e,r){return r?await T({port:e,host:r})?e:null:await T({port:e})&&await T({port:e,host:"0.0.0.0"})?e:null}async function y(e,r=20,t){let o=Math.floor(e);for(let c=0;c<r;c+=1){if(o>=1&&o<=65535){const i=await D(o,t);if(i!==null)return i}o+=1}return await D(0,t)??e}async function te(e=x,r=B()){const t=await y(e,20,r);return k(t),process.env.AWS_RUNTIME_BRIDGE_PORT=String(t),t!==e&&h.warn(`[runtime-bridge] \u9996\u9009\u7AEF\u53E3 ${e} \u5DF2\u88AB\u5360\u7528\uFF0C\u81EA\u52A8\u6539\u7528 ${t} \u542F\u52A8`),t}const S="http://localhost:8080";function d(e){return e==null?void 0:String(e).trim()||void 0}function g(e){const r=d(e);if(!r)return;const t=r.replace(/^((?:https?|wss?):\/\/(?:\[[^\]]+\]|[^/:?#]+):\d+):\d+(?=\/|$)/i,"$1");try{const o=new URL(t);return o.protocol==="ws:"?o.protocol="http:":o.protocol==="wss:"?o.protocol="https:":o.protocol=o.protocol.toLowerCase(),o.hostname=o.hostname.toLowerCase(),o.origin}catch{return t.replace(/\/+$/,"")}}function F(){return n.join(R(),".aws-bridge","config.json")}function b(){return n.join(R(),".aws-bridge","bridge-runtime.properties")}function re(){const e=b();a.mkdirSync(n.dirname(e),{recursive:!0});const r=[`port=${j()}`,`pid=${process.pid}`,`startedAt=${new Date().toISOString()}`];a.writeFileSync(e,`${r.join(`
|
|
2
2
|
`)}
|
|
3
|
-
`,{encoding:"utf8",mode:384})}function
|
|
3
|
+
`,{encoding:"utf8",mode:384})}function A(){const e=F();try{if(!a.existsSync(e))return[];const r=JSON.parse(a.readFileSync(e,"utf-8")),t=i=>({serverUrl:g(i.serverUrl)||g(i.schedulerBaseUrl),instanceId:d(i.instanceId),instanceName:d(i.instanceName),userKey:d(i.userKey)}),s=(Array.isArray(r.autoRegisterTargets)?r.autoRegisterTargets:[]).filter(i=>!!(i&&typeof i=="object"&&!Array.isArray(i))).map(t).filter(i=>!!i.serverUrl);if(s.length>0)return s;const c=t(r);return c.serverUrl?[c]:[]}catch{return[]}}function G(){const r=A().map(t=>t.serverUrl).filter(t=>!!t);return Array.from(new Set(r))}function K(){return A().length}function ne(){return V(void 0)}function V(e,r,t){const o=g(e);if(o)return{url:o,source:"request",ambiguousTargetUrls:[]};const s=typeof r=="string"?r.trim():"",c=typeof t=="string"?t.trim():"";if(s||c){const f=A();let u;if(s&&(u=f.find(_=>_.instanceId===s)),!u&&c&&(u=f.find(_=>_.instanceName===c)),!u&&s&&!c&&(u=f.find(_=>_.instanceName===s)),u?.serverUrl)return{url:u.serverUrl,source:"instance-id-match",ambiguousTargetUrls:[],instanceId:u.instanceId,instanceName:u.instanceName,userKey:u.userKey}}const i=g(process.env.AWS_RUNTIME_SCHEDULER_BASE_URL);if(i)return{url:i,source:"env",ambiguousTargetUrls:[]};const l=G(),O=K();return O===1&&l.length===1?{url:l[0]||S,source:"single-auto-register-target",ambiguousTargetUrls:[],userKey:A()[0]?.userKey}:O>1||l.length>1?{url:S,source:"ambiguous-auto-register-targets",ambiguousTargetUrls:l}:{url:S,source:"default",ambiguousTargetUrls:[]}}const oe=g(process.env.AWS_RUNTIME_SCHEDULER_BASE_URL)||S,ie=process.env.NODE_ENV||"development",se=process.env.AWS_ALLOW_HOST_FILE_BROWSER==="true",ce=String(process.env.AWS_RUNTIME_CORS_ORIGINS||"http://localhost:3000,http://127.0.0.1:3000,http://localhost:5173,http://127.0.0.1:5173").split(",").map(e=>e.trim()).filter(e=>e.length>0);function ue(){}function ae(e){return String(process.env.AWS_RUNTIME_CLAUDE_CONFIG_FILE||"").trim()||n.join(e,".claude","settings.json")}function pe(e){return String(process.env.AWS_RUNTIME_CLAUDE_MCP_CONFIG_FILE||"").trim()||n.join(e,".claude.json")}function le(e){return String(process.env.AWS_RUNTIME_CLAUDE_SKILLS_DIR||"").trim()||n.join(e,".claude","skills")}function _e(e){return String(process.env.AWS_RUNTIME_OPENCODE_CONFIG_FILE||"").trim()||n.join(e,".config","opencode","opencode.json")}function P(){return n.join(R(),".aws-bridge")}function ge(){return n.join(P(),"instance-template")}function p(e){return n.join(P(),"instance-runtime",H(String(e)))}function Ee(e){return n.join(p(e),"config.json")}function Se(e){return n.join(p(e),"skills")}function de(e){return n.join(p(e),"plugins")}function Ae(e){return n.join(p(e),"private-skills")}function fe(e){return n.join(p(e),"private-skills.json")}function Re(e){return n.join(p(e),"mcp-extra.json")}function me(){return String(process.env.ACODE_HOME||"").trim()||n.join(U(),".acode")}function Te(e){return String(process.env.AWS_RUNTIME_CODEX_CONFIG_FILE||"").trim()||n.join(e,".codex","config.toml")}function Ie(e){return String(process.env.AWS_RUNTIME_CODEX_SKILLS_DIR||"").trim()||n.join(e,".codex","skills")}function Oe(e){return String(process.env.AWS_RUNTIME_OPENCODE_SKILLS_DIR||"").trim()||n.join(e,".opencode","skills")}const Ne=Number(process.env.AWS_ORPHAN_SCAN_INTERVAL||3e4),ve=process.env.AWS_ORPHAN_AUTO_CLEAN_MODE||"alert",Ue=process.env.AWS_ORPHAN_SCAN_ENABLED!=="false",xe=Number(process.env.AWS_ORPHAN_UNRESPONSIVE_TIMEOUT||3e5),De=Number(process.env.AWS_ORPHAN_CPU_THRESHOLD||100),Pe=Number(process.env.AWS_ORPHAN_MEMORY_THRESHOLD||2048),Le=process.env.AWS_AUTO_REGISTER==="true",Ce=process.env.AWS_TENANT_ID||"",he=process.env.AWS_USER_KEY||"",He=process.env.AWS_INSTANCE_NAME||"",Be=process.env.AWS_PROJECT_NAME||"",Me=process.env.AWS_ROLE_NAME||"",We=process.env.AWS_WORKSPACE_PATH||"",we=process.env.AWS_REGISTER_IP||process.env.AWS_VIRTUAL_IP||"";let I;function je(){if(I!==void 0)return I;let e="unknown";try{const r=n.dirname(N(import.meta.url)),t=n.resolve(r,"..","package.json");a.existsSync(t)&&(e=JSON.parse(a.readFileSync(t,"utf-8")).version||"unknown")}catch{}return I=e,e}export{Le as AUTO_REGISTER_ENABLED,He as AUTO_REGISTER_INSTANCE_NAME,Be as AUTO_REGISTER_PROJECT_NAME,Me as AUTO_REGISTER_ROLE_NAME,Ce as AUTO_REGISTER_TENANT_ID,he as AUTO_REGISTER_USER_KEY,we as AUTO_REGISTER_VIRTUAL_IP,We as AUTO_REGISTER_WORKSPACE_PATH,W as DEFAULT_BRIDGE_PORT,S as DEFAULT_SCHEDULER_BASE_URL,w as DEV_DEFAULT_BRIDGE_PORT,ve as ORPHAN_AUTO_CLEAN_MODE,De as ORPHAN_CPU_THRESHOLD,Pe as ORPHAN_MEMORY_THRESHOLD,Ue as ORPHAN_SCAN_ENABLED,Ne as ORPHAN_SCAN_INTERVAL,xe as ORPHAN_UNRESPONSIVE_TIMEOUT,se as allowHostFileBrowser,ce as allowedCorsOrigins,y as findAvailableListenPort,me as getAcodeDataHome,j as getActiveBridgeHttpPort,F as getAutoRegisterConfigFilePath,P as getBridgeDataHome,Ee as getBridgeInstanceConfigFile,Re as getBridgeInstanceMcpExtraFile,de as getBridgeInstancePluginsDir,Ae as getBridgeInstancePrivateSkillsDir,fe as getBridgeInstancePrivateSkillsManifest,p as getBridgeInstanceRuntimeDir,Se as getBridgeInstanceSkillsDir,B as getBridgeListenHost,b as getBridgeRuntimePropertiesFilePath,ge as getBridgeTemplateDir,je as getBridgeVersion,ae as getClaudeConfigFile,pe as getClaudeMcpConfigFile,le as getClaudeSkillsDir,Te as getCodexConfigFile,Ie as getCodexSkillsDir,_e as getOpencodeConfigFile,Oe as getOpencodeSkillsDir,R as getRuntimeHomeDir,Q as getShellPairToken,U as getUserHomeDir,Z as isDesktopAppMode,v as isDevMode,ie as nodeEnv,x as port,te as reserveBridgeListenPort,ee as resetActiveBridgeHttpPort,ne as resolveSchedulerBaseUrl,V as resolveSchedulerBaseUrlFrom,oe as schedulerBaseUrl,k as setActiveBridgeHttpPort,ue as validateProductionToken,re as writeBridgeRuntimePropertiesFile};
|
|
4
4
|
|
package/dist/index.js
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
import{existsSync as L,readFileSync as G}from"node:fs";import O from"node:os";import P from"node:path";import{pathToFileURL as j}from"node:url";import{sweepExpiredJournals as K}from"@agentswork/acode";import N from"cors";import I from"express";import{adapterRegistry as _}from"./adapter/index.js";import{attachBrowserWebSocketServer as H}from"./browser/browser-ws-bridge.js";import{getAcodeDataHome as W,getActiveBridgeHttpPort as k,getAutoRegisterConfigFilePath as U,getBridgeDataHome as J,getBridgeListenHost as z,getBridgeRuntimePropertiesFilePath as Y,getBridgeTemplateConfigFile as Z,reserveBridgeListenPort as q,validateProductionToken as Q,writeBridgeRuntimePropertiesFile as V}from"./config.js";import{attachRemoteDesktopWebSocketServer as X}from"./remote-desktop/index.js";import{acodeTodosRouter as ee}from"./routes/acode-todos.js";import{agentStateRouter as re}from"./routes/agent-state.js";import{aiSourcesRouter as te}from"./routes/ai-sources.js";import{backgroundTasksRouter as ie}from"./routes/background-tasks.js";import{bridgeTempFilesRouter as oe}from"./routes/bridge-temp-files.js";import{browserListenersRouter as ne}from"./routes/browser-listeners.js";import{browserSessionsRouter as se}from"./routes/browser-sessions.js";import{capabilitiesRouter as ae}from"./routes/capabilities.js";import{computerRouter as me}from"./routes/computer.js";import{dashboardRouter as ue}from"./routes/dashboard.js";import{debugMountRouter as ce}from"./routes/debug-mount.js";import{desktopControlRouter as de}from"./routes/desktop-control.js";import{eventsRouter as ge}from"./routes/events.js";import{fileBrowserRouter as pe}from"./routes/file-browser.js";import{fileChangeDiffRouter as fe}from"./routes/file-change-diff.js";import{fileDiffRollbackRouter as le}from"./routes/file-diff-rollback.js";import{fileSnapshotRouter as be}from"./routes/file-snapshot.js";import{gitRouter as he}from"./routes/git.js";import{instanceRouter as we,setGracefulShutdownFn as Re}from"./routes/instance.js";import{jdksRouter as Se}from"./routes/jdks.js";import{launchRouter as Pe}from"./routes/launch.js";import{lspProvidersRouter as ye}from"./routes/lsp-providers.js";import{attachLspWebSocketServer as $e}from"./routes/lsp.js";import{ltrRouter as Ie}from"./routes/ltr.js";import{mcpExtraRouter as ke}from"./routes/mcp-extra.js";import{mcpRouter as Ce}from"./routes/mcp.js";import{pluginsRouter as Ae}from"./routes/plugins.js";import{processesRouter as ve}from"./routes/processes.js";import{propertiesRouter as Be}from"./routes/properties.js";import{attachPtyWebSocketServer as Te,closeAllPtySessions as De,ptyRouter as Me,ptySessions as Ee}from"./routes/pty.js";import{runtimeBindingRouter as xe,logRuntimeBindingStartupState as Fe}from"./routes/runtime-binding.js";import{sessionsRouter as Le}from"./routes/sessions.js";import{skillsRouter as Ge}from"./routes/skills.js";import{subAgentsRouter as Oe}from"./routes/sub-agents.js";import{systemMetricsRouter as je}from"./routes/system-metrics.js";import{taskContextRouter as Ke}from"./routes/task-context.js";import{techStackRouter as Ne}from"./routes/tech-stack.js";import{terminalRouter as _e,sdkSessions as S}from"./routes/terminal.js";import{workspaceIndexRouter as He}from"./routes/workspace-index.js";import{ymlRouter as We}from"./routes/yml.js";import{accessControlMiddleware as Ue}from"./services/access-control.js";import{ensureAcodePackageReleased as Je,getReleasedAcodeEntryPath as ze}from"./services/acode-package.js";import{getAgentProcessManager as C}from"./services/agent-process-manager.js";import{autoRegister as Ye,unregister as Ze,bridgeRestartCleanup as qe,cancelBackgroundRegisterRetries as Qe}from"./services/auto-register.js";import{ensureAwsClientAgentMcpReleased as Ve}from"./services/aws-client-agent-mcp.js";import{disposeBrowserSessionManager as Xe}from"./services/browser-session-manager.js";import{handleCliCommand as er}from"./services/cli-commands.js";import{disposeDesktopMcpManager as rr}from"./services/desktop-mcp-manager.js";import{getLaunchManager as tr}from"./services/launch-manager.js";import{migrateOldPathsOnStartup as ir}from"./services/legacy-path-migration.js";import{deliverPendingBridgeLifecycleNotifications as or}from"./services/lifecycle-state.js";import{startLogRetention as nr}from"./services/log-retention.js";import{startOrphanMonitor as sr,stopOrphanMonitor as ar}from"./services/orphan-monitor.js";import{pluginManager as mr}from"./services/plugin-manager.js";import{detectOrphanProcesses as ur}from"./services/process-detector.js";import{buildGracefulShutdownPlan as cr,shouldCleanupPersistedSessionsOnStartup as dr}from"./services/runtime-lifecycle-policy.js";import{ensureStartupConfig as gr}from"./services/startup-config-wizard.js";import{subAgentStore as pr}from"./services/sub-agent-manager-instance.js";import{loadPersistedSessions as A,savePersistedSessions as v}from"./services/terminal-persistence.js";import{stopTunnelClient as fr}from"./services/tunnel-client.js";import{loadDynamicModule as B}from"./utils/dynamic-import.js";import{logger as e}from"./utils/logger.js";async function lr(){const w=await er();w.handled&&process.exit(w.exitCode),await gr(),Q(),Ve(),Je(),ir(),Fe(),await q(),V(),e.info(`[runtime-bridge] \u5DF2\u5199\u5165\u8FD0\u884C\u65F6\u914D\u7F6E ${Y()}\uFF08port=${k()}\uFF09`),e.info(`[runtime-bridge] ACode \u6570\u636E\u76EE\u5F55(\u7528\u6237): ${W()}`),e.info(`[runtime-bridge] Bridge \u6570\u636E\u76EE\u5F55: ${J()}`),e.info(`[runtime-bridge] \u6A21\u677F\u914D\u7F6E: ${Z()}`),K().then(r=>{r>0&&e.info(`[runtime-bridge] \u5DF2\u6E05\u626B ${r} \u4E2A\u8D85\u671F\u4F11\u7720 journal`)}).catch(()=>{});async function T(){try{if(await Ye())e.info("[runtime-bridge] \u81EA\u52A8\u6CE8\u518C\u6210\u529F");else{const{loadConfig:n}=await import("./services/auto-register.js"),o=n();!!o.userKey&&o.enabled?e.warn("[runtime-bridge] \u81EA\u52A8\u6CE8\u518C\u6682\u65F6\u5931\u8D25\uFF0C\u5C06\u5728\u540E\u53F0\u6301\u7EED\u91CD\u8BD5\u76F4\u5230\u4E0E\u8C03\u5EA6\u4E2D\u5FC3\u5EFA\u7ACB\u8FDE\u63A5"):(e.info("[runtime-bridge] \u81EA\u52A8\u6CE8\u518C\u672A\u914D\u7F6E\uFF0C\u7EE7\u7EED\u542F\u52A8\u670D\u52A1"),e.info(`[runtime-bridge] \u8981\u542F\u7528\u81EA\u52A8\u6CE8\u518C\uFF0C\u8BF7\u521B\u5EFA\u914D\u7F6E\u6587\u4EF6 ${U()}`))}}catch(r){const n=r;e.warn("[runtime-bridge] \u81EA\u52A8\u6CE8\u518C\u51FA\u9519:",n.message)}}T().then(()=>D()).then(()=>or()).then(()=>{e.info("[runtime-bridge] Bridge \u751F\u547D\u5468\u671F\u901A\u77E5\u540C\u6B65\u5B8C\u6210")}).catch(r=>{e.warn("[runtime-bridge] \u81EA\u52A8\u6CE8\u518C\u6216\u6E05\u7406\u51FA\u9519:",r)}),import("./services/update-notifier.js").then(({startUpdateNotifier:r})=>r()).catch(r=>{e.warn("[runtime-bridge] \u7248\u672C\u68C0\u67E5\u670D\u52A1\u542F\u52A8\u5931\u8D25:",r.message)});async function D(){try{if(process.env.AWS_BRIDGE_RESTART_CLEANUP!=="true"){e.info("[runtime-bridge] \u8DF3\u8FC7 Bridge \u91CD\u542F\u6E05\u7406\uFF0C\u4FDD\u7559 Agent \u72B6\u6001\u4F9B\u8C03\u5EA6\u4E2D\u5FC3\u6062\u590D");return}const{getRegistrationState:r}=await import("./services/auto-register.js"),n=r();if(!n.registered||!n.instanceId){e.info("[runtime-bridge] \u5B9E\u4F8B\u672A\u6CE8\u518C\uFF0C\u8DF3\u8FC7 Bridge \u91CD\u542F\u6E05\u7406");return}e.info("[runtime-bridge] \u2605 Bridge \u91CD\u542F\u6E05\u7406\u5DF2\u663E\u5F0F\u542F\u7528\uFF0C\u6B63\u5728\u901A\u77E5\u8C03\u5EA6\u4E2D\u5FC3\u6E05\u7406 Agent \u72B6\u6001...");const o=await qe();o.success?e.info(`[runtime-bridge] \u2605 Bridge \u91CD\u542F\u6E05\u7406\u6210\u529F\uFF0C\u6E05\u7406\u4E86 ${o.agentCount||0} \u4E2A Agent`):e.warn(`[runtime-bridge] \u2605 Bridge \u91CD\u542F\u6E05\u7406\u5931\u8D25: ${o.error}`)}catch(r){const n=r;e.warn("[runtime-bridge] Bridge \u91CD\u542F\u6E05\u7406\u51FA\u9519:",n.message)}}async function M(){try{const r=await A();if(r.length===0){e.info("[runtime-bridge] \u65E0\u6301\u4E45\u5316\u4F1A\u8BDD\uFF0C\u8DF3\u8FC7\u8FDB\u7A0B\u6CE8\u518C\u8868\u91CD\u5EFA");return}await C().rebuildRegistry(r.map(o=>({agentId:o.agentId,sessionId:o.sessionId,pid:o.pid,workspacePath:o.workspacePath,command:o.command,mode:"sdk"}))),e.info(`[runtime-bridge] \u8FDB\u7A0B\u6CE8\u518C\u8868\u91CD\u5EFA\u5B8C\u6210: ${r.length} \u6761\u8BB0\u5F55`)}catch(r){const n=r;e.warn("[runtime-bridge] \u8FDB\u7A0B\u6CE8\u518C\u8868\u91CD\u5EFA\u5931\u8D25:",n.message)}}M().catch(r=>{e.warn("[runtime-bridge] \u8FDB\u7A0B\u6CE8\u518C\u8868\u91CD\u5EFA\u5931\u8D25:",r)}),B(j(P.join(ze(),"..","background-command-manager.js")).href).then(async r=>{const n=r.backgroundCommandManager;if(!n||typeof n.reconcileAllAgents!="function"){e.warn("[runtime-bridge] \u540E\u53F0\u547D\u4EE4\u7BA1\u7406\u5668\u4E0D\u53EF\u7528\uFF0C\u8DF3\u8FC7\u542F\u52A8\u5B64\u513F\u5BF9\u8D26");return}const o=await n.reconcileAllAgents();o>0&&e.info(`[runtime-bridge] \u2605 \u542F\u52A8\u5B64\u513F\u5BF9\u8D26\u5B8C\u6210\uFF1A\u4FEE\u590D ${o} \u6761\u540E\u53F0\u547D\u4EE4\u72B6\u6001`)}).catch(r=>{e.warn("[runtime-bridge] \u542F\u52A8\u5B64\u513F\u5BF9\u8D26\u5931\u8D25:",r.message)});async function E(){try{const r=await import("node:fs/promises"),n=await import("node:path"),o=await import("node:os"),d=n.join(o.tmpdir(),"agentswork-runtime-bridge",".preserve-sessions");let u=!1;try{const t=await r.readFile(d,"utf-8");u=JSON.parse(t).preserveSessions===!0,await r.unlink(d),e.info(`[runtime-bridge] \u2605 \u68C0\u6D4B\u5230\u4FDD\u7559\u4F1A\u8BDD\u6807\u8BB0\uFF0CpreserveSessions=${u}`)}catch{}const a=await A();if(a.length===0){e.info("[runtime-bridge] \u542F\u52A8\u65F6\u65E0\u6301\u4E45\u5316\u4F1A\u8BDD\uFF0C\u65E0\u9700\u68C0\u6D4B\u5B64\u513F\u8FDB\u7A0B");return}if(!dr(u)){e.info(`[runtime-bridge] \u2605 \u4FDD\u7559 ${a.length} \u4E2A\u6301\u4E45\u5316\u4F1A\u8BDD\u5E76\u91CD\u5EFA\u8FDB\u7A0B\u6CE8\u518C\u8868`),await C().rebuildRegistry(a.map(s=>({agentId:s.agentId,sessionId:s.sessionId,pid:s.pid,workspacePath:s.workspacePath,command:s.command,mode:"sdk"})));return}e.info(`[runtime-bridge] \u2605 \u5DF2\u663E\u5F0F\u542F\u7528\u542F\u52A8\u6E05\u7406\uFF0C\u68C0\u6D4B ${a.length} \u4E2A\u6301\u4E45\u5316\u4F1A\u8BDD\u7684\u5B64\u513F\u8FDB\u7A0B...`);const g=await ur(a.map(t=>({agentId:t.agentId,pid:t.pid,workspacePath:t.workspacePath,command:t.command})));if(g.length>0){e.warn(`[runtime-bridge] \u2605 \u68C0\u6D4B\u5230 ${g.length} \u4E2A\u5B64\u513F\u8FDB\u7A0B\u4ECD\u5728\u8FD0\u884C\uFF1A`);for(const t of g)e.warn(` - agentId=${t.agentId}, pid=${t.process.pid}, command=${t.process.command?.slice(0,50)}`);e.info("[runtime-bridge] \u6B63\u5728\u81EA\u52A8\u6E05\u7406\u6240\u6709\u5B64\u513F\u8FDB\u7A0B...");for(const t of g)try{if(t.process.pid)if(process.platform==="win32"){const{execSync:s}=await import("node:child_process");s(`taskkill /PID ${t.process.pid} /T /F`,{encoding:"utf8",timeout:3e3}),e.info(`[runtime-bridge] \u5DF2\u81EA\u52A8\u7EC8\u6B62\u5B64\u513F\u8FDB\u7A0B: agentId=${t.agentId}, PID=${t.process.pid}`)}else process.kill(t.process.pid,"SIGKILL"),e.info(`[runtime-bridge] \u5DF2\u81EA\u52A8\u7EC8\u6B62\u5B64\u513F\u8FDB\u7A0B: agentId=${t.agentId}, PID=${t.process.pid}`)}catch(s){const c=s;e.warn(`[runtime-bridge] \u81EA\u52A8\u7EC8\u6B62\u5B64\u513F\u8FDB\u7A0B\u5931\u8D25: agentId=${t.agentId}, PID=${t.process.pid}, error=${c.message}`)}await new Promise(t=>setTimeout(t,1e3))}await v([]),e.info(`[runtime-bridge] \u2605 \u542F\u52A8\u6E05\u7406\u5B8C\u6210\uFF0C\u5DF2\u6E05\u7A7A\u6240\u6709\u6301\u4E45\u5316\u4F1A\u8BDD\uFF08\u6E05\u7406\u4E86 ${g.length} \u4E2A\u5B64\u513F\u8FDB\u7A0B\uFF09`)}catch(r){const n=r;e.warn("[runtime-bridge] \u542F\u52A8\u65F6\u5B64\u513F\u8FDB\u7A0B\u68C0\u6D4B\u5931\u8D25:",n.message)}}E().catch(r=>{e.warn("[runtime-bridge] \u5B64\u513F\u8FDB\u7A0B\u68C0\u6D4B\u51FA\u9519:",r)}),sr().catch(r=>{e.warn("[runtime-bridge] \u542F\u52A8\u5B64\u513F\u8FDB\u7A0B\u76D1\u63A7\u5931\u8D25:",r)});const i=I();i.use(Ue),i.use(N()),i.use(I.json({limit:"1mb"})),i.use("/runtime",xe),i.use("/runtime",Be),i.use("/runtime",We),i.use("/runtime",we),i.use("/runtime",Ge),i.use("/runtime",Ce),i.use("/runtime",ae),i.use("/runtime",_e),i.use("/runtime",Le),i.use("/runtime",ve),i.use("/runtime",Pe),i.use("/runtime",Se),i.use("/runtime",Ne),i.use("/runtime",je),i.use("/runtime",ge),i.use("/runtime",he),i.use("/runtime",be),i.use("/runtime",ee),i.use("/runtime",re),i.use("/runtime",ie),i.use("/runtime",Oe),i.use("/runtime",se),i.use("/runtime",de),i.use("/runtime",ne),i.use("/runtime",Ae),i.use("/runtime",ke),i.use("/runtime",ce),i.use("/runtime",te),i.use("/runtime",Ke),i.use("/runtime",le),i.use("/runtime",fe),i.use("/runtime",ye),i.use("/runtime/computer",me),i.use("/pty",Me),i.use("/",ue),i.use("/api/file-browser",pe),i.use("/api",He),i.use("/api/ltr",Ie),i.use("/api/bridge-temp-files",oe);function x(){const r=k(),n=z(),o=n?i.listen(r,n,()=>{e.info(`[runtime-bridge] listening on ${n}:${r}`)}):i.listen(r,()=>{e.info(`[runtime-bridge] listening on ${r}`)});return Te(o),X(o),H(o),$e(o),o.on("error",d=>{if(d.code==="EADDRINUSE"){e.error(`[runtime-bridge] port ${r} became unavailable after reservation (another process grabbed it concurrently). Set AWS_RUNTIME_BRIDGE_PORT to a free port and restart.`),process.exitCode=1;return}e.error("[runtime-bridge] failed to start server:",d),process.exitCode=1}),o}let y=!1;async function l(r,n,o=!1){if(y){e.info(`[runtime-bridge] \u5DF2\u5728\u5173\u95ED\u4E2D\uFF0C\u5FFD\u7565 ${r}`);return}y=!0,o||R()&&(o=!0,e.info("[runtime-bridge] \u2605 \u68C0\u6D4B\u5230 .preserve-sessions \u6807\u8BB0\u6587\u4EF6\uFF0C\u81EA\u52A8\u5347\u7EA7\u4E3A\u4FDD\u7559\u4F1A\u8BDD\u6A21\u5F0F")),e.info(`[runtime-bridge] \u6536\u5230 ${r} \u4FE1\u53F7\uFF0C\u5F00\u59CB\u4F18\u96C5\u5173\u95ED... (preserveSessions=${o})`);const d=Date.now(),u=cr(o);try{const a=S.size;if(u.terminateSdkSessions){e.info(`[runtime-bridge] \u6B63\u5728\u505C\u6B62 ${a} \u4E2A SDK \u4F1A\u8BDD...`);for(const[t,s]of S.entries())try{const c=s.providerId||"claude-code",p=_.get(c);let f="";try{const m=p.getSessionPid?.(t);m&&(f=` (PID: ${m})`)}catch{}await p.terminateSession(t),e.info(`[runtime-bridge] SDK \u4F1A\u8BDD ${t} \u5DF2\u7EC8\u6B62${f}`),S.delete(t)}catch(c){const p=c;e.error(`[runtime-bridge] SDK \u4F1A\u8BDD ${t} \u7EC8\u6B62\u5931\u8D25:`,p.message),S.delete(t)}}else e.info(`[runtime-bridge] \u2605 \u4FDD\u7559 ${a} \u4E2A SDK \u4F1A\u8BDD\uFF0C\u4E0D\u5728\u91CD\u542F\u6062\u590D\u573A\u666F\u4E2D\u7EC8\u6B62 Agent \u8FDB\u7A0B`);const h=Ee.size;u.closePtySessions?(e.info(`[runtime-bridge] \u6B63\u5728\u505C\u6B62 ${h} \u4E2A PTY \u4F1A\u8BDD...`),De("shutdown")):e.info(`[runtime-bridge] \u2605 \u4FDD\u7559 ${h} \u4E2A PTY \u4F1A\u8BDD\uFF0C\u4E0D\u5728\u91CD\u542F\u6062\u590D\u573A\u666F\u4E2D\u5173\u95ED\u7EC8\u7AEF\u8FDB\u7A0B`);try{const{running:t,stopped:s}=await tr().stopAll();t>0&&e.info(`[runtime-bridge] \u542F\u52A8\u9879\u8FDB\u7A0B\u5DF2\u505C\u6B62: running=${t}, stopped=${s}`)}catch(t){e.warn("[runtime-bridge] \u505C\u6B62\u542F\u52A8\u9879\u8FDB\u7A0B\u5931\u8D25:",t.message)}e.info("[runtime-bridge] \u6B63\u5728\u505C\u6B62\u5B64\u513F\u8FDB\u7A0B\u76D1\u63A7...");try{const t="file://"+P.join(import.meta.dirname,"..","package","acode","dist","background-command-manager.js"),c=(await B(t).catch(()=>({backgroundCommandManager:null}))).backgroundCommandManager;c&&(e.info("[runtime-bridge] \u6B63\u5728\u6E05\u7406\u540E\u53F0\u547D\u4EE4..."),await c.disposeAll())}catch(t){e.warn("[runtime-bridge] \u540E\u53F0\u547D\u4EE4\u6E05\u7406\u5931\u8D25: %s",t?.message)}if(ar(),u.terminateResidualProcesses&&(e.info("[runtime-bridge] \u7B49\u5F85\u8FDB\u7A0B\u5B8C\u5168\u7EC8\u6B62..."),await new Promise(t=>setTimeout(t,1e3))),u.terminateResidualProcesses)try{const{detectOrphanProcesses:t,terminateProcessTree:s}=await import("./services/process-detector.js"),{loadPersistedSessions:c}=await import("./services/terminal-persistence.js"),p=await c();if(p.length>0){const f=await t(p.map(m=>({agentId:m.agentId,pid:m.pid,workspacePath:m.workspacePath,command:m.command})));if(f.length>0){e.warn(`[runtime-bridge] \u68C0\u6D4B\u5230 ${f.length} \u4E2A\u6B8B\u7559\u8FDB\u7A0B\uFF0C\u6B63\u5728\u5F3A\u5236\u7EC8\u6B62...`);for(const m of f)if(m.process.pid){const F=await s(m.process.pid);e.info(`[runtime-bridge] \u5DF2\u5F3A\u5236\u7EC8\u6B62\u6B8B\u7559\u8FDB\u7A0B\u6811\uFF1AagentId=${m.agentId}, PID=${m.process.pid}, \u7EC8\u6B62\u4E86 ${F.terminated} \u4E2A\u8FDB\u7A0B`)}}}}catch(t){const s=t;e.warn("[runtime-bridge] \u6B8B\u7559\u8FDB\u7A0B\u68C0\u67E5\u5931\u8D25:",s.message)}else e.info("[runtime-bridge] \u2605 \u4FDD\u7559\u6A21\u5F0F\u8DF3\u8FC7\u6B8B\u7559\u8FDB\u7A0B\u5F3A\u5236\u7EC8\u6B62\uFF0C\u7B49\u5F85\u8C03\u5EA6\u4E2D\u5FC3\u6062\u590D\u4F1A\u8BDD");if(u.unregisterInstance){e.info("[runtime-bridge] \u6B63\u5728\u6CE8\u9500\u5B9E\u4F8B...");try{await Ze()}catch(t){const s=t;e.error("[runtime-bridge] \u6CE8\u9500\u5B9E\u4F8B\u5931\u8D25:",s.message)}}else e.info("[runtime-bridge] \u2605 \u4FDD\u7559\u6A21\u5F0F\u8DF3\u8FC7\u5B9E\u4F8B\u6CE8\u9500\uFF0C\u907F\u514D\u8C03\u5EA6\u4E2D\u5FC3\u5C06 Agent \u6807\u8BB0\u4E3A stopped");if(Qe(),u.stopTunnelClient&&(e.info("[runtime-bridge] \u6B63\u5728\u5173\u95ED\u96A7\u9053\u5BA2\u6237\u7AEF..."),fr()),u.clearPersistedSessions){e.info("[runtime-bridge] \u6B63\u5728\u6E05\u7A7A\u6301\u4E45\u5316\u4F1A\u8BDD\u72B6\u6001...");try{await v([])}catch(t){const s=t;e.error("[runtime-bridge] \u6E05\u7A7A\u6301\u4E45\u5316\u72B6\u6001\u5931\u8D25:",s.message)}}else e.info("[runtime-bridge] \u2605 \u4FDD\u7559\u6301\u4E45\u5316\u4F1A\u8BDD\u72B6\u6001\uFF08aws-mcp-server \u91CD\u542F\u6062\u590D\u573A\u666F\uFF09");try{await Xe(),e.info("[runtime-bridge] browser \u5DE5\u5177\u6808\u5DF2\u6E05\u7406")}catch(t){e.warn("[runtime-bridge] browser \u5DE5\u5177\u6808\u6E05\u7406\u5931\u8D25:",t.message)}try{await rr(),e.info("[runtime-bridge] desktop \u5DE5\u5177\u6808\u5DF2\u6E05\u7406")}catch(t){e.warn("[runtime-bridge] desktop \u5DE5\u5177\u6808\u6E05\u7406\u5931\u8D25:",t.message)}try{await mr.stopAll(),e.info("[runtime-bridge] \u63D2\u4EF6\u76D1\u542C\u8FDB\u7A0B\u5DF2\u6E05\u7406")}catch(t){e.warn("[runtime-bridge] \u63D2\u4EF6\u76D1\u542C\u8FDB\u7A0B\u6E05\u7406\u5931\u8D25:",t.message)}const g=Date.now()-d;e.info(`[runtime-bridge] \u4F18\u96C5\u5173\u95ED\u5B8C\u6210 (\u8017\u65F6 ${g}ms)\uFF0C\u505C\u6B62 ${a} SDK \u4F1A\u8BDD`),n.close(()=>{e.info("[runtime-bridge] HTTP \u670D\u52A1\u5668\u5DF2\u5173\u95ED"),process.exit(process.exitCode||0)}),setTimeout(()=>{e.warn("[runtime-bridge] \u4F18\u96C5\u5173\u95ED\u8D85\u65F6\uFF0C\u5F3A\u5236\u9000\u51FA"),process.exit(1)},15e3)}catch(a){const h=a;e.error("[runtime-bridge] \u4F18\u96C5\u5173\u95ED\u8FC7\u7A0B\u4E2D\u53D1\u751F\u9519\u8BEF:",h),process.exit(1)}}pr.reconcileZombies().then(r=>{r>0&&e.info(`[runtime-bridge] \u5DF2\u6E05\u7406 ${r} \u4E2A\u50F5\u5C38 sub-agent \u8BB0\u5F55`)}).catch(r=>{e.warn("[runtime-bridge] \u6E05\u7406\u50F5\u5C38 sub-agent \u8BB0\u5F55\u5931\u8D25:",r.message)});const b=x();nr();const $=P.join(O.tmpdir(),"agentswork-runtime-bridge",".preserve-sessions");function R(){try{if(L($)){const r=G($,"utf-8");return JSON.parse(r).preserveSessions===!0}}catch{}return!1}Re(async(r,n)=>{await l(r,b,n)}),process.on("SIGTERM",()=>{const r=R();l("SIGTERM",b,r)}),process.on("SIGINT",()=>{const r=R();l("SIGINT",b,r)}),process.platform==="win32"&&process.on("SIGBREAK",()=>{const r=R();l("SIGBREAK",b,r)}),process.on("uncaughtException",r=>{e.error("[runtime-bridge] \u672A\u6355\u83B7\u5F02\u5E38:",r),l("uncaughtException",b)}),process.on("unhandledRejection",r=>{e.error("[runtime-bridge] \u672A\u5904\u7406\u7684 Promise \u62D2\u7EDD:",r)})}lr().catch(w=>{e.error("[runtime-bridge] \u542F\u52A8\u5931\u8D25:",w),process.exitCode=1});
|
|
2
|
+
import{existsSync as G,readFileSync as O}from"node:fs";import j from"node:os";import P from"node:path";import{pathToFileURL as K}from"node:url";import{sweepExpiredJournals as N}from"@agentswork/acode";import _ from"cors";import $ from"express";import{adapterRegistry as W}from"./adapter/index.js";import{attachBrowserWebSocketServer as H}from"./browser/browser-ws-bridge.js";import{getAcodeDataHome as U,getActiveBridgeHttpPort as k,getAutoRegisterConfigFilePath as J,getBridgeDataHome as z,getBridgeListenHost as Y,getBridgeRuntimePropertiesFilePath as Z,reserveBridgeListenPort as q,validateProductionToken as Q,writeBridgeRuntimePropertiesFile as V}from"./config.js";import{attachRemoteDesktopWebSocketServer as X}from"./remote-desktop/index.js";import{acodeTodosRouter as ee}from"./routes/acode-todos.js";import{agentStateRouter as re}from"./routes/agent-state.js";import{aiSourcesRouter as te}from"./routes/ai-sources.js";import{backgroundTasksRouter as ie}from"./routes/background-tasks.js";import{bridgeTempFilesRouter as oe}from"./routes/bridge-temp-files.js";import{browserListenersRouter as ne}from"./routes/browser-listeners.js";import{browserSessionsRouter as se}from"./routes/browser-sessions.js";import{capabilitiesRouter as ae}from"./routes/capabilities.js";import{computerRouter as me}from"./routes/computer.js";import{dashboardRouter as ue}from"./routes/dashboard.js";import{debugMountRouter as ce}from"./routes/debug-mount.js";import{desktopControlRouter as de}from"./routes/desktop-control.js";import{eventsRouter as pe}from"./routes/events.js";import{fileBrowserRouter as ge}from"./routes/file-browser.js";import{fileChangeDiffRouter as fe}from"./routes/file-change-diff.js";import{fileDiffRollbackRouter as le}from"./routes/file-diff-rollback.js";import{fileSnapshotRouter as be}from"./routes/file-snapshot.js";import{gitRouter as he}from"./routes/git.js";import{instanceRouter as we,setGracefulShutdownFn as Re}from"./routes/instance.js";import{jdksRouter as Se}from"./routes/jdks.js";import{launchRouter as Pe}from"./routes/launch.js";import{lspProvidersRouter as ye}from"./routes/lsp-providers.js";import{attachLspWebSocketServer as Ie}from"./routes/lsp.js";import{ltrRouter as $e}from"./routes/ltr.js";import{mediaFilesRouter as ke}from"./routes/media-files.js";import{mcpExtraRouter as Ce}from"./routes/mcp-extra.js";import{mcpRouter as Ae}from"./routes/mcp.js";import{pluginsRouter as ve}from"./routes/plugins.js";import{pluginUiRouter as Be}from"./routes/plugin-ui.js";import{processesRouter as Te}from"./routes/processes.js";import{propertiesRouter as De}from"./routes/properties.js";import{attachPtyWebSocketServer as Me,closeAllPtySessions as Ee,ptyRouter as xe,ptySessions as Fe}from"./routes/pty.js";import{runtimeBindingRouter as Le,logRuntimeBindingStartupState as Ge}from"./routes/runtime-binding.js";import{sessionsRouter as Oe}from"./routes/sessions.js";import{skillsRouter as je}from"./routes/skills.js";import{subAgentsRouter as Ke}from"./routes/sub-agents.js";import{systemMetricsRouter as Ne}from"./routes/system-metrics.js";import{taskContextRouter as _e}from"./routes/task-context.js";import{techStackRouter as We}from"./routes/tech-stack.js";import{terminalRouter as He,sdkSessions as S}from"./routes/terminal.js";import{workspaceIndexRouter as Ue}from"./routes/workspace-index.js";import{ymlRouter as Je}from"./routes/yml.js";import{accessControlMiddleware as ze}from"./services/access-control.js";import{ensureAcodePackageReleased as Ye,getReleasedAcodeEntryPath as Ze}from"./services/acode-package.js";import{getAgentProcessManager as C}from"./services/agent-process-manager.js";import{autoRegister as qe,unregister as Qe,bridgeRestartCleanup as Ve,cancelBackgroundRegisterRetries as Xe}from"./services/auto-register.js";import{ensureAwsClientAgentMcpReleased as er}from"./services/aws-client-agent-mcp.js";import{disposeBrowserSessionManager as rr}from"./services/browser-session-manager.js";import{handleCliCommand as tr}from"./services/cli-commands.js";import{disposeDesktopMcpManager as ir}from"./services/desktop-mcp-manager.js";import{getLaunchManager as or}from"./services/launch-manager.js";import{migrateOldPathsOnStartup as nr}from"./services/legacy-path-migration.js";import{deliverPendingBridgeLifecycleNotifications as sr}from"./services/lifecycle-state.js";import{startLogRetention as ar}from"./services/log-retention.js";import{startOrphanMonitor as mr,stopOrphanMonitor as ur}from"./services/orphan-monitor.js";import{pluginManager as cr}from"./services/plugin-manager.js";import{pluginUiStatusWatcher as A}from"./services/plugin-ui-status-runtime.js";import{detectOrphanProcesses as dr}from"./services/process-detector.js";import{buildGracefulShutdownPlan as pr,shouldCleanupPersistedSessionsOnStartup as gr}from"./services/runtime-lifecycle-policy.js";import{ensureStartupConfig as fr}from"./services/startup-config-wizard.js";import{subAgentStore as lr}from"./services/sub-agent-manager-instance.js";import{loadPersistedSessions as v,savePersistedSessions as B}from"./services/terminal-persistence.js";import{stopTunnelClient as br}from"./services/tunnel-client.js";import{loadDynamicModule as T}from"./utils/dynamic-import.js";import{logger as e}from"./utils/logger.js";async function hr(){const w=await tr();w.handled&&process.exit(w.exitCode),await fr(),Q(),er(),Ye(),nr(),Ge(),await q(),V(),e.info(`[runtime-bridge] \u5DF2\u5199\u5165\u8FD0\u884C\u65F6\u914D\u7F6E ${Z()}\uFF08port=${k()}\uFF09`),e.info(`[runtime-bridge] ACode \u6570\u636E\u76EE\u5F55(\u7528\u6237): ${U()}`),e.info(`[runtime-bridge] Bridge \u6570\u636E\u76EE\u5F55: ${z()}`),N().then(r=>{r>0&&e.info(`[runtime-bridge] \u5DF2\u6E05\u626B ${r} \u4E2A\u8D85\u671F\u4F11\u7720 journal`)}).catch(()=>{});async function D(){try{if(await qe())e.info("[runtime-bridge] \u81EA\u52A8\u6CE8\u518C\u6210\u529F");else{const{loadConfig:n}=await import("./services/auto-register.js"),o=n();!!o.userKey&&o.enabled?e.warn("[runtime-bridge] \u81EA\u52A8\u6CE8\u518C\u6682\u65F6\u5931\u8D25\uFF0C\u5C06\u5728\u540E\u53F0\u6301\u7EED\u91CD\u8BD5\u76F4\u5230\u4E0E\u8C03\u5EA6\u4E2D\u5FC3\u5EFA\u7ACB\u8FDE\u63A5"):(e.info("[runtime-bridge] \u81EA\u52A8\u6CE8\u518C\u672A\u914D\u7F6E\uFF0C\u7EE7\u7EED\u542F\u52A8\u670D\u52A1"),e.info(`[runtime-bridge] \u8981\u542F\u7528\u81EA\u52A8\u6CE8\u518C\uFF0C\u8BF7\u521B\u5EFA\u914D\u7F6E\u6587\u4EF6 ${J()}`))}}catch(r){const n=r;e.warn("[runtime-bridge] \u81EA\u52A8\u6CE8\u518C\u51FA\u9519:",n.message)}}D().then(()=>M()).then(()=>sr()).then(()=>{e.info("[runtime-bridge] Bridge \u751F\u547D\u5468\u671F\u901A\u77E5\u540C\u6B65\u5B8C\u6210")}).catch(r=>{e.warn("[runtime-bridge] \u81EA\u52A8\u6CE8\u518C\u6216\u6E05\u7406\u51FA\u9519:",r)}),import("./services/update-notifier.js").then(({startUpdateNotifier:r})=>r()).catch(r=>{e.warn("[runtime-bridge] \u7248\u672C\u68C0\u67E5\u670D\u52A1\u542F\u52A8\u5931\u8D25:",r.message)});async function M(){try{if(process.env.AWS_BRIDGE_RESTART_CLEANUP!=="true"){e.info("[runtime-bridge] \u8DF3\u8FC7 Bridge \u91CD\u542F\u6E05\u7406\uFF0C\u4FDD\u7559 Agent \u72B6\u6001\u4F9B\u8C03\u5EA6\u4E2D\u5FC3\u6062\u590D");return}const{getRegistrationState:r}=await import("./services/auto-register.js"),n=r();if(!n.registered||!n.instanceId){e.info("[runtime-bridge] \u5B9E\u4F8B\u672A\u6CE8\u518C\uFF0C\u8DF3\u8FC7 Bridge \u91CD\u542F\u6E05\u7406");return}e.info("[runtime-bridge] \u2605 Bridge \u91CD\u542F\u6E05\u7406\u5DF2\u663E\u5F0F\u542F\u7528\uFF0C\u6B63\u5728\u901A\u77E5\u8C03\u5EA6\u4E2D\u5FC3\u6E05\u7406 Agent \u72B6\u6001...");const o=await Ve();o.success?e.info(`[runtime-bridge] \u2605 Bridge \u91CD\u542F\u6E05\u7406\u6210\u529F\uFF0C\u6E05\u7406\u4E86 ${o.agentCount||0} \u4E2A Agent`):e.warn(`[runtime-bridge] \u2605 Bridge \u91CD\u542F\u6E05\u7406\u5931\u8D25: ${o.error}`)}catch(r){const n=r;e.warn("[runtime-bridge] Bridge \u91CD\u542F\u6E05\u7406\u51FA\u9519:",n.message)}}async function E(){try{const r=await v();if(r.length===0){e.info("[runtime-bridge] \u65E0\u6301\u4E45\u5316\u4F1A\u8BDD\uFF0C\u8DF3\u8FC7\u8FDB\u7A0B\u6CE8\u518C\u8868\u91CD\u5EFA");return}await C().rebuildRegistry(r.map(o=>({agentId:o.agentId,sessionId:o.sessionId,pid:o.pid,workspacePath:o.workspacePath,command:o.command,mode:"sdk"}))),e.info(`[runtime-bridge] \u8FDB\u7A0B\u6CE8\u518C\u8868\u91CD\u5EFA\u5B8C\u6210: ${r.length} \u6761\u8BB0\u5F55`)}catch(r){const n=r;e.warn("[runtime-bridge] \u8FDB\u7A0B\u6CE8\u518C\u8868\u91CD\u5EFA\u5931\u8D25:",n.message)}}E().catch(r=>{e.warn("[runtime-bridge] \u8FDB\u7A0B\u6CE8\u518C\u8868\u91CD\u5EFA\u5931\u8D25:",r)}),T(K(P.join(Ze(),"..","background-command-manager.js")).href).then(async r=>{const n=r.backgroundCommandManager;if(!n||typeof n.reconcileAllAgents!="function"){e.warn("[runtime-bridge] \u540E\u53F0\u547D\u4EE4\u7BA1\u7406\u5668\u4E0D\u53EF\u7528\uFF0C\u8DF3\u8FC7\u542F\u52A8\u5B64\u513F\u5BF9\u8D26");return}const o=await n.reconcileAllAgents();o>0&&e.info(`[runtime-bridge] \u2605 \u542F\u52A8\u5B64\u513F\u5BF9\u8D26\u5B8C\u6210\uFF1A\u4FEE\u590D ${o} \u6761\u540E\u53F0\u547D\u4EE4\u72B6\u6001`)}).catch(r=>{e.warn("[runtime-bridge] \u542F\u52A8\u5B64\u513F\u5BF9\u8D26\u5931\u8D25:",r.message)});async function x(){try{const r=await import("node:fs/promises"),n=await import("node:path"),o=await import("node:os"),d=n.join(o.tmpdir(),"agentswork-runtime-bridge",".preserve-sessions");let u=!1;try{const t=await r.readFile(d,"utf-8");u=JSON.parse(t).preserveSessions===!0,await r.unlink(d),e.info(`[runtime-bridge] \u2605 \u68C0\u6D4B\u5230\u4FDD\u7559\u4F1A\u8BDD\u6807\u8BB0\uFF0CpreserveSessions=${u}`)}catch{}const a=await v();if(a.length===0){e.info("[runtime-bridge] \u542F\u52A8\u65F6\u65E0\u6301\u4E45\u5316\u4F1A\u8BDD\uFF0C\u65E0\u9700\u68C0\u6D4B\u5B64\u513F\u8FDB\u7A0B");return}if(!gr(u)){e.info(`[runtime-bridge] \u2605 \u4FDD\u7559 ${a.length} \u4E2A\u6301\u4E45\u5316\u4F1A\u8BDD\u5E76\u91CD\u5EFA\u8FDB\u7A0B\u6CE8\u518C\u8868`),await C().rebuildRegistry(a.map(s=>({agentId:s.agentId,sessionId:s.sessionId,pid:s.pid,workspacePath:s.workspacePath,command:s.command,mode:"sdk"})));return}e.info(`[runtime-bridge] \u2605 \u5DF2\u663E\u5F0F\u542F\u7528\u542F\u52A8\u6E05\u7406\uFF0C\u68C0\u6D4B ${a.length} \u4E2A\u6301\u4E45\u5316\u4F1A\u8BDD\u7684\u5B64\u513F\u8FDB\u7A0B...`);const p=await dr(a.map(t=>({agentId:t.agentId,pid:t.pid,workspacePath:t.workspacePath,command:t.command})));if(p.length>0){e.warn(`[runtime-bridge] \u2605 \u68C0\u6D4B\u5230 ${p.length} \u4E2A\u5B64\u513F\u8FDB\u7A0B\u4ECD\u5728\u8FD0\u884C\uFF1A`);for(const t of p)e.warn(` - agentId=${t.agentId}, pid=${t.process.pid}, command=${t.process.command?.slice(0,50)}`);e.info("[runtime-bridge] \u6B63\u5728\u81EA\u52A8\u6E05\u7406\u6240\u6709\u5B64\u513F\u8FDB\u7A0B...");for(const t of p)try{if(t.process.pid)if(process.platform==="win32"){const{execSync:s}=await import("node:child_process");s(`taskkill /PID ${t.process.pid} /T /F`,{encoding:"utf8",timeout:3e3}),e.info(`[runtime-bridge] \u5DF2\u81EA\u52A8\u7EC8\u6B62\u5B64\u513F\u8FDB\u7A0B: agentId=${t.agentId}, PID=${t.process.pid}`)}else process.kill(t.process.pid,"SIGKILL"),e.info(`[runtime-bridge] \u5DF2\u81EA\u52A8\u7EC8\u6B62\u5B64\u513F\u8FDB\u7A0B: agentId=${t.agentId}, PID=${t.process.pid}`)}catch(s){const c=s;e.warn(`[runtime-bridge] \u81EA\u52A8\u7EC8\u6B62\u5B64\u513F\u8FDB\u7A0B\u5931\u8D25: agentId=${t.agentId}, PID=${t.process.pid}, error=${c.message}`)}await new Promise(t=>setTimeout(t,1e3))}await B([]),e.info(`[runtime-bridge] \u2605 \u542F\u52A8\u6E05\u7406\u5B8C\u6210\uFF0C\u5DF2\u6E05\u7A7A\u6240\u6709\u6301\u4E45\u5316\u4F1A\u8BDD\uFF08\u6E05\u7406\u4E86 ${p.length} \u4E2A\u5B64\u513F\u8FDB\u7A0B\uFF09`)}catch(r){const n=r;e.warn("[runtime-bridge] \u542F\u52A8\u65F6\u5B64\u513F\u8FDB\u7A0B\u68C0\u6D4B\u5931\u8D25:",n.message)}}x().catch(r=>{e.warn("[runtime-bridge] \u5B64\u513F\u8FDB\u7A0B\u68C0\u6D4B\u51FA\u9519:",r)}),mr().catch(r=>{e.warn("[runtime-bridge] \u542F\u52A8\u5B64\u513F\u8FDB\u7A0B\u76D1\u63A7\u5931\u8D25:",r)});const i=$();i.use(ze),i.use(_()),i.use($.json({limit:"1mb"})),i.use("/runtime",Le),i.use("/runtime",De),i.use("/runtime",Je),i.use("/runtime",we),i.use("/runtime",je),i.use("/runtime",Ae),i.use("/runtime",ae),i.use("/runtime",He),i.use("/runtime",Oe),i.use("/runtime",Te),i.use("/runtime",Pe),i.use("/runtime",Se),i.use("/runtime",We),i.use("/runtime",Ne),i.use("/runtime",pe),i.use("/runtime",he),i.use("/runtime",be),i.use("/runtime",ee),i.use("/runtime",re),i.use("/runtime",ie),i.use("/runtime",Ke),i.use("/runtime",se),i.use("/runtime",de),i.use("/runtime",ne),i.use("/runtime",ve),i.use("/runtime",Be),i.use("/runtime",Ce),i.use("/runtime",ce),i.use("/runtime",te),i.use("/runtime",_e),i.use("/runtime",le),i.use("/runtime",fe),i.use("/runtime",ke),i.use("/runtime",ye),i.use("/runtime/computer",me),i.use("/pty",xe),i.use("/",ue),i.use("/api/file-browser",ge),i.use("/api",Ue),i.use("/api/ltr",$e),i.use("/api/bridge-temp-files",oe);function F(){const r=k(),n=Y(),o=n?i.listen(r,n,()=>{e.info(`[runtime-bridge] listening on ${n}:${r}`)}):i.listen(r,()=>{e.info(`[runtime-bridge] listening on ${r}`)});return Me(o),X(o),H(o),Ie(o),o.on("error",d=>{if(d.code==="EADDRINUSE"){e.error(`[runtime-bridge] port ${r} became unavailable after reservation (another process grabbed it concurrently). Set AWS_RUNTIME_BRIDGE_PORT to a free port and restart.`),process.exitCode=1;return}e.error("[runtime-bridge] failed to start server:",d),process.exitCode=1}),o}let y=!1;async function l(r,n,o=!1){if(y){e.info(`[runtime-bridge] \u5DF2\u5728\u5173\u95ED\u4E2D\uFF0C\u5FFD\u7565 ${r}`);return}y=!0,o||R()&&(o=!0,e.info("[runtime-bridge] \u2605 \u68C0\u6D4B\u5230 .preserve-sessions \u6807\u8BB0\u6587\u4EF6\uFF0C\u81EA\u52A8\u5347\u7EA7\u4E3A\u4FDD\u7559\u4F1A\u8BDD\u6A21\u5F0F")),e.info(`[runtime-bridge] \u6536\u5230 ${r} \u4FE1\u53F7\uFF0C\u5F00\u59CB\u4F18\u96C5\u5173\u95ED... (preserveSessions=${o})`);const d=Date.now(),u=pr(o);try{const a=S.size;if(u.terminateSdkSessions){e.info(`[runtime-bridge] \u6B63\u5728\u505C\u6B62 ${a} \u4E2A SDK \u4F1A\u8BDD...`);for(const[t,s]of S.entries())try{const c=s.providerId||"claude-code",g=W.get(c);let f="";try{const m=g.getSessionPid?.(t);m&&(f=` (PID: ${m})`)}catch{}await g.terminateSession(t),e.info(`[runtime-bridge] SDK \u4F1A\u8BDD ${t} \u5DF2\u7EC8\u6B62${f}`),S.delete(t)}catch(c){const g=c;e.error(`[runtime-bridge] SDK \u4F1A\u8BDD ${t} \u7EC8\u6B62\u5931\u8D25:`,g.message),S.delete(t)}}else e.info(`[runtime-bridge] \u2605 \u4FDD\u7559 ${a} \u4E2A SDK \u4F1A\u8BDD\uFF0C\u4E0D\u5728\u91CD\u542F\u6062\u590D\u573A\u666F\u4E2D\u7EC8\u6B62 Agent \u8FDB\u7A0B`);const h=Fe.size;u.closePtySessions?(e.info(`[runtime-bridge] \u6B63\u5728\u505C\u6B62 ${h} \u4E2A PTY \u4F1A\u8BDD...`),Ee("shutdown")):e.info(`[runtime-bridge] \u2605 \u4FDD\u7559 ${h} \u4E2A PTY \u4F1A\u8BDD\uFF0C\u4E0D\u5728\u91CD\u542F\u6062\u590D\u573A\u666F\u4E2D\u5173\u95ED\u7EC8\u7AEF\u8FDB\u7A0B`);try{const{running:t,stopped:s}=await or().stopAll();t>0&&e.info(`[runtime-bridge] \u542F\u52A8\u9879\u8FDB\u7A0B\u5DF2\u505C\u6B62: running=${t}, stopped=${s}`)}catch(t){e.warn("[runtime-bridge] \u505C\u6B62\u542F\u52A8\u9879\u8FDB\u7A0B\u5931\u8D25:",t.message)}e.info("[runtime-bridge] \u6B63\u5728\u505C\u6B62\u5B64\u513F\u8FDB\u7A0B\u76D1\u63A7...");try{const t="file://"+P.join(import.meta.dirname,"..","package","acode","dist","background-command-manager.js"),c=(await T(t).catch(()=>({backgroundCommandManager:null}))).backgroundCommandManager;c&&(e.info("[runtime-bridge] \u6B63\u5728\u6E05\u7406\u540E\u53F0\u547D\u4EE4..."),await c.disposeAll())}catch(t){e.warn("[runtime-bridge] \u540E\u53F0\u547D\u4EE4\u6E05\u7406\u5931\u8D25: %s",t?.message)}if(ur(),u.terminateResidualProcesses&&(e.info("[runtime-bridge] \u7B49\u5F85\u8FDB\u7A0B\u5B8C\u5168\u7EC8\u6B62..."),await new Promise(t=>setTimeout(t,1e3))),u.terminateResidualProcesses)try{const{detectOrphanProcesses:t,terminateProcessTree:s}=await import("./services/process-detector.js"),{loadPersistedSessions:c}=await import("./services/terminal-persistence.js"),g=await c();if(g.length>0){const f=await t(g.map(m=>({agentId:m.agentId,pid:m.pid,workspacePath:m.workspacePath,command:m.command})));if(f.length>0){e.warn(`[runtime-bridge] \u68C0\u6D4B\u5230 ${f.length} \u4E2A\u6B8B\u7559\u8FDB\u7A0B\uFF0C\u6B63\u5728\u5F3A\u5236\u7EC8\u6B62...`);for(const m of f)if(m.process.pid){const L=await s(m.process.pid);e.info(`[runtime-bridge] \u5DF2\u5F3A\u5236\u7EC8\u6B62\u6B8B\u7559\u8FDB\u7A0B\u6811\uFF1AagentId=${m.agentId}, PID=${m.process.pid}, \u7EC8\u6B62\u4E86 ${L.terminated} \u4E2A\u8FDB\u7A0B`)}}}}catch(t){const s=t;e.warn("[runtime-bridge] \u6B8B\u7559\u8FDB\u7A0B\u68C0\u67E5\u5931\u8D25:",s.message)}else e.info("[runtime-bridge] \u2605 \u4FDD\u7559\u6A21\u5F0F\u8DF3\u8FC7\u6B8B\u7559\u8FDB\u7A0B\u5F3A\u5236\u7EC8\u6B62\uFF0C\u7B49\u5F85\u8C03\u5EA6\u4E2D\u5FC3\u6062\u590D\u4F1A\u8BDD");if(u.unregisterInstance){e.info("[runtime-bridge] \u6B63\u5728\u6CE8\u9500\u5B9E\u4F8B...");try{await Qe()}catch(t){const s=t;e.error("[runtime-bridge] \u6CE8\u9500\u5B9E\u4F8B\u5931\u8D25:",s.message)}}else e.info("[runtime-bridge] \u2605 \u4FDD\u7559\u6A21\u5F0F\u8DF3\u8FC7\u5B9E\u4F8B\u6CE8\u9500\uFF0C\u907F\u514D\u8C03\u5EA6\u4E2D\u5FC3\u5C06 Agent \u6807\u8BB0\u4E3A stopped");if(Xe(),u.stopTunnelClient&&(e.info("[runtime-bridge] \u6B63\u5728\u5173\u95ED\u96A7\u9053\u5BA2\u6237\u7AEF..."),br()),u.clearPersistedSessions){e.info("[runtime-bridge] \u6B63\u5728\u6E05\u7A7A\u6301\u4E45\u5316\u4F1A\u8BDD\u72B6\u6001...");try{await B([])}catch(t){const s=t;e.error("[runtime-bridge] \u6E05\u7A7A\u6301\u4E45\u5316\u72B6\u6001\u5931\u8D25:",s.message)}}else e.info("[runtime-bridge] \u2605 \u4FDD\u7559\u6301\u4E45\u5316\u4F1A\u8BDD\u72B6\u6001\uFF08aws-mcp-server \u91CD\u542F\u6062\u590D\u573A\u666F\uFF09");try{await rr(),e.info("[runtime-bridge] browser \u5DE5\u5177\u6808\u5DF2\u6E05\u7406")}catch(t){e.warn("[runtime-bridge] browser \u5DE5\u5177\u6808\u6E05\u7406\u5931\u8D25:",t.message)}try{await ir(),e.info("[runtime-bridge] desktop \u5DE5\u5177\u6808\u5DF2\u6E05\u7406")}catch(t){e.warn("[runtime-bridge] desktop \u5DE5\u5177\u6808\u6E05\u7406\u5931\u8D25:",t.message)}try{A.stop(),await cr.stopAll(),e.info("[runtime-bridge] \u63D2\u4EF6\u76D1\u542C\u8FDB\u7A0B\u5DF2\u6E05\u7406")}catch(t){e.warn("[runtime-bridge] \u63D2\u4EF6\u76D1\u542C\u8FDB\u7A0B\u6E05\u7406\u5931\u8D25:",t.message)}const p=Date.now()-d;e.info(`[runtime-bridge] \u4F18\u96C5\u5173\u95ED\u5B8C\u6210 (\u8017\u65F6 ${p}ms)\uFF0C\u505C\u6B62 ${a} SDK \u4F1A\u8BDD`),n.close(()=>{e.info("[runtime-bridge] HTTP \u670D\u52A1\u5668\u5DF2\u5173\u95ED"),process.exit(process.exitCode||0)}),setTimeout(()=>{e.warn("[runtime-bridge] \u4F18\u96C5\u5173\u95ED\u8D85\u65F6\uFF0C\u5F3A\u5236\u9000\u51FA"),process.exit(1)},15e3)}catch(a){const h=a;e.error("[runtime-bridge] \u4F18\u96C5\u5173\u95ED\u8FC7\u7A0B\u4E2D\u53D1\u751F\u9519\u8BEF:",h),process.exit(1)}}lr.reconcileZombies().then(r=>{r>0&&e.info(`[runtime-bridge] \u5DF2\u6E05\u7406 ${r} \u4E2A\u50F5\u5C38 sub-agent \u8BB0\u5F55`)}).catch(r=>{e.warn("[runtime-bridge] \u6E05\u7406\u50F5\u5C38 sub-agent \u8BB0\u5F55\u5931\u8D25:",r.message)});const b=F();A.start(),ar();const I=P.join(j.tmpdir(),"agentswork-runtime-bridge",".preserve-sessions");function R(){try{if(G(I)){const r=O(I,"utf-8");return JSON.parse(r).preserveSessions===!0}}catch{}return!1}Re(async(r,n)=>{await l(r,b,n)}),process.on("SIGTERM",()=>{const r=R();l("SIGTERM",b,r)}),process.on("SIGINT",()=>{const r=R();l("SIGINT",b,r)}),process.platform==="win32"&&process.on("SIGBREAK",()=>{const r=R();l("SIGBREAK",b,r)}),process.on("uncaughtException",r=>{e.error("[runtime-bridge] \u672A\u6355\u83B7\u5F02\u5E38:",r),l("uncaughtException",b)}),process.on("unhandledRejection",r=>{e.error("[runtime-bridge] \u672A\u5904\u7406\u7684 Promise \u62D2\u7EDD:",r)})}hr().catch(w=>{e.error("[runtime-bridge] \u542F\u52A8\u5931\u8D25:",w),process.exitCode=1});
|
|
3
3
|
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
import{promises as n}from"node:fs";import c from"node:path";import{Router as y}from"express";import{validateToken as d}from"../middleware/auth.js";import{ensureInsideWorkspace as p,resolveWorkspaceRoot as w}from"../utils/path-utils.js";import{createLogger as k}from"../utils/logger.js";const l=k("media-files"),u=y(),v=20*1024*1024,h=200*1024*1024;function f(t){if(typeof t!="string"||!t.trim())throw new Error("relativePath is required");const e=t.trim().replace(/\\/g,"/");if(c.isAbsolute(e)||/^[a-zA-Z]:/.test(e)||e.includes(".."))throw new Error(`relativePath must be a workspace-relative path without traversal: ${e}`);if(e.endsWith("/"))throw new Error(`relativePath must point to a file, not a directory: ${e}`);return e}function g(t,e){if(!t||!String(t).trim())throw new Error("workspacePath is required");const r=w(t),o=p(r,c.join(r,f(e)));return{root:r,target:o}}u.post("/media-write",d,async(t,e)=>{try{const{workspacePath:r,relativePath:o,contentBase64:a}=t.body??{},{target:i}=g(r,o);if(typeof a!="string"||!a){e.status(400).json({ok:!1,error:"contentBase64 is required"});return}const s=Buffer.from(a,"base64");if(s.length===0){e.status(400).json({ok:!1,error:"content is empty"});return}if(s.length>h){e.status(413).json({ok:!1,error:`content exceeds ${h} bytes`});return}await n.mkdir(c.dirname(i),{recursive:!0}),await n.writeFile(i,s),l.info(`media-write: ${i} (${s.length} bytes)`),e.json({ok:!0,relativePath:f(o),fullPath:i,size:s.length})}catch(r){const o=r.message??"media-write failed";l.warn(`media-write failed: ${o}`),e.status(400).json({ok:!1,error:o})}}),u.post("/media-read",d,async(t,e)=>{try{const{workspacePath:r,relativePath:o}=t.body??{},{target:a}=g(r,o),i=typeof t.body?.maxBytes=="number"&&t.body.maxBytes>0?t.body.maxBytes:v,s=await n.stat(a);if(!s.isFile()){e.status(400).json({ok:!1,error:`not a regular file: ${a}`});return}if(s.size>i){e.status(413).json({ok:!1,error:`file exceeds maxBytes (${s.size} > ${i})`});return}const m=await n.readFile(a);l.info(`media-read: ${a} (${m.length} bytes)`),e.json({ok:!0,relativePath:f(o),size:s.size,contentBase64:m.toString("base64")})}catch(r){const a=r.code==="ENOENT"?`file not found: ${String(t.body?.relativePath??"")}`:r.message??"media-read failed";l.warn(`media-read failed: ${a}`),e.status(400).json({ok:!1,error:a})}});export{u as mediaFilesRouter};
|
|
2
|
+
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
import{existsSync as M,readFileSync as O,statSync as v}from"node:fs";import{normalize as R,resolve as A,sep as T}from"node:path";import{Router as _}from"express";import{validateToken as d}from"../middleware/auth.js";import{pluginManager as h}from"../services/plugin-manager.js";import{pluginUiStatusWatcher as C}from"../services/plugin-ui-status-runtime.js";import{requireAgentOwnership as w,requireUserScope as j}from"../services/user-scope.js";import{createLogger as L}from"../utils/logger.js";const E=L("plugin-ui"),k=_(),z=20*1024*1024,B=64*1024,D={".html":"text/html; charset=utf-8",".js":"text/javascript; charset=utf-8",".mjs":"text/javascript; charset=utf-8",".css":"text/css; charset=utf-8",".svg":"image/svg+xml",".png":"image/png",".jpg":"image/jpeg",".jpeg":"image/jpeg",".gif":"image/gif",".webp":"image/webp",".ico":"image/x-icon",".json":"application/json; charset=utf-8",".woff":"font/woff",".woff2":"font/woff2",".ttf":"font/ttf",".map":"application/json; charset=utf-8",".txt":"text/plain; charset=utf-8",".wasm":"application/wasm"};function S(o){return(t,n)=>{o(t,n).catch(e=>{E.error("[plugin-ui] %s %s \u5931\u8D25: %s",t.method,t.path,e.message),n.headersSent||n.status(500).json({ok:!1,error:e.message})})}}k.get("/plugin-ui/snapshot",d,j,S(async(o,t)=>{const e=String(o.query.agentIds??"").trim().split(",").map(s=>s.trim()).filter(Boolean).slice(0,200);if(e.length===0){t.status(400).json({ok:!1,error:"agentIds is required"});return}const a={};for(const s of e)try{a[s]=C.snapshot(s)}catch{a[s]={}}t.json({ok:!0,snapshots:a})})),k.get("/plugin-ui/:agentId/snapshot",d,j,w,S(async(o,t)=>{const n=String(o.params.agentId??"").trim();if(!n){t.status(400).json({ok:!1,error:"agentId is required"});return}t.json({ok:!0,agentId:n,statuses:C.snapshot(n)})})),k.post("/plugin-ui/:agentId/:name/invoke",d,j,w,S(async(o,t)=>{const n=Date.now(),e=String(o.params.agentId??"").trim(),a=String(o.params.name??"").trim();if(!e||!a){t.status(400).json({ok:!1,error:"agentId and name are required"});return}const s=o.body??{},l=typeof s.tool=="string"?s.tool.trim():"";if(!l){t.status(400).json({ok:!1,error:"tool is required"});return}const p=(await h.list(e)).find(r=>r.name===a),i=p?.frontend;if(!p||!p.enabled||!i){t.status(404).json({ok:!1,error:"\u63D2\u4EF6\u4E0D\u5B58\u5728\u6216\u672A\u542F\u7528\u524D\u7AEF\u5165\u53E3"});return}const f=new Set(i.view?.invoke??[]);if(i.status?.tool&&f.add(i.status.tool),!f.has(l)){t.status(403).json({ok:!1,error:`\u5DE5\u5177 "${l}" \u4E0D\u5728\u63D2\u4EF6 ui \u58F0\u660E\u767D\u540D\u5355\u5185`});return}if(s.params!==void 0&&(typeof s.params!="object"||s.params===null||Array.isArray(s.params))){t.status(400).json({ok:!1,error:"params \u987B\u4E3A JSON \u5BF9\u8C61"});return}if(s.params!==void 0&&JSON.stringify(s.params).length>B){t.status(413).json({ok:!1,error:"params \u8D85\u51FA\u4F53\u79EF\u4E0A\u9650"});return}const u=await h.invokeTool(e,a,l,s.params??{});E.info("[plugin-ui][invoke] agent=%s plugin=%s tool=%s ok=%s durationMs=%d",e,a,l,u.ok,Date.now()-n),t.status(u.ok?200:400).json(u)})),k.get("/plugin-ui/:agentId/:name/assets/*",d,j,w,S(async(o,t)=>{const n=String(o.params.agentId??"").trim(),e=String(o.params.name??"").trim(),a=String(o.params[0]??"");if(!n||!e){t.status(400).json({ok:!1,error:"agentId and name are required"});return}const s=a.replace(/^\/+/,"");if(!s){t.status(400).json({ok:!1,error:"asset path is required"});return}const g=R(s).replace(/^([.][.](\/|\\|$))+/,"").split(T).join("/");if(!g.startsWith("ui/")||g.includes("..")){t.status(400).json({ok:!1,error:"\u975E\u6CD5\u7684\u8D44\u6E90\u8DEF\u5F84"});return}const i=(await h.list(n)).find(m=>m.name===e);if(!i||!i.enabled){t.status(404).json({ok:!1,error:"\u63D2\u4EF6\u4E0D\u5B58\u5728\u6216\u5DF2\u505C\u7528"});return}const f=await h.getEnabledPluginDir(n,e);if(!f){t.status(404).json({ok:!1,error:"\u63D2\u4EF6\u4E0D\u5B58\u5728\u6216\u5DF2\u505C\u7528"});return}const u=A(f),r=A(u,g);if(r!==u&&!r.startsWith(u+T)){t.status(400).json({ok:!1,error:"\u975E\u6CD5\u7684\u8D44\u6E90\u8DEF\u5F84"});return}if(!M(r)||!v(r).isFile()){t.status(404).json({ok:!1,error:"\u8D44\u6E90\u4E0D\u5B58\u5728"});return}const y=r.slice(r.lastIndexOf(".")).toLowerCase()||"",I=D[y];if(!I){t.status(415).json({ok:!1,error:"\u4E0D\u652F\u6301\u7684\u8D44\u6E90\u7C7B\u578B"});return}const x=v(r).size;if(x>z){t.status(413).json({ok:!1,error:"\u8D44\u6E90\u8D85\u51FA\u4F53\u79EF\u4E0A\u9650"});return}const b=O(r),c={"Content-Type":I,"Cache-Control":"no-store","X-Content-Type-Options":"nosniff"};if(y===".html"){const m=b.toString("utf8").replace(/<head([^>]*)>/i,'<head$1><base href="./">');c["Content-Length"]=String(Buffer.byteLength(m)),t.set(c),t.send(m);return}c["Content-Length"]=String(x),t.set(c),t.send(b)}));export{k as pluginUiRouter};
|
|
2
|
+
|
package/dist/routes/plugins.d.ts
CHANGED
package/dist/routes/plugins.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{Router as
|
|
1
|
+
import{Router as N}from"express";import{raw as k}from"express";import{validateToken as u,validateTokenOrLoopback as y}from"../middleware/auth.js";import{assertAgentOwnership as j}from"../services/agent-ownership.js";import{getEffective as O,setDefault as P,setInherited as A,setOverride as B}from"../services/capability-config.js";import{isValidPluginName as f}from"../services/plugin-manifest.js";import{pluginManager as g}from"../services/plugin-manager.js";import{PluginWecomCallbackService as x}from"../services/plugin-wecom-callback.js";import{pluginUiStatusWatcher as S}from"../services/plugin-ui-status-runtime.js";import{getUserScopeOrThrow as b,requireAgentOwnership as p,requireUserScope as c}from"../services/user-scope.js";import{createLogger as C}from"../utils/logger.js";const E=C("plugins"),r=N();function i(n){return(t,s)=>{n(t,s).catch(e=>{if(E.error("[plugins] %s %s \u5931\u8D25: %s",t.method,t.path,e.message),!s.headersSent){const a=e.message.includes("agent-ownership-mismatch")?403:500;s.status(a).json({ok:!1,error:e.message})}})}}r.get("/plugins/deployed",u,c,i(async(n,t)=>{const s=b(n),a=(await g.listDeployed(s)).map(o=>({...o,enabled:O(s,"","plugins",o.pluginName)}));t.json({ok:!0,deployedPlugins:a})})),r.post("/plugins/deployed/default",u,c,i(async(n,t)=>{const s=String((n.body??{})?.pluginName??"").trim();if(!f(s)){t.status(400).json({ok:!1,error:"pluginName \u975E\u6CD5\uFF08\u987B\u4E3A kebab-case\uFF0C1~64 \u5B57\u7B26\uFF09"});return}const e=String((n.body??{})?.agentId??"").trim(),a=(n.body??{})?.enabled,o=a==null?null:!!a,l=b(n);if(e){if(!j(e,l)){t.status(403).json({ok:!1,error:"agent-ownership-mismatch"});return}B(l,e,"plugins",s,o)}else P(l,"plugins",s,o);t.json({ok:!0,pluginName:s,agentId:e,enabled:o})})),r.post("/plugins/deployed/inherited",u,c,i(async(n,t)=>{const s=String((n.body??{})?.agentId??"").trim();if(!s){t.status(400).json({ok:!1,error:"agentId is required"});return}const e=b(n);if(!j(s,e)){t.status(403).json({ok:!1,error:"agent-ownership-mismatch"});return}const a=(n.body??{})?.map;A(e,s,"plugins",a??null),t.json({ok:!0,agentId:s,count:Object.keys(a??{}).length})})),r.post("/plugins/deployed/remove",u,c,i(async(n,t)=>{const s=String((n.body??{})?.pluginName??"").trim();if(!f(s)){t.status(400).json({ok:!1,error:"pluginName \u975E\u6CD5\uFF08\u987B\u4E3A kebab-case\uFF0C1~64 \u5B57\u7B26\uFF09"});return}const e=b(n),a=await g.removeDeployedPlugin(s,e);t.status(a.ok?200:400).json(a)})),r.get("/plugins/:agentId",u,c,p,i(async(n,t)=>{const s=String(n.params.agentId??"").trim();if(!s){t.status(400).json({ok:!1,error:"agentId is required"});return}const e=await g.list(s);S.refreshAgent(s).catch(()=>{}),t.json({ok:!0,agentId:s,plugins:e})})),r.post("/plugins/:agentId/install",u,c,p,i(async(n,t)=>{const s=String(n.params.agentId??"").trim(),e=n.body??{},a=typeof e.source=="string"?e.source:"",o=e.config&&typeof e.config=="object"&&!Array.isArray(e.config)?Object.fromEntries(Object.entries(e.config).filter(d=>typeof d[1]=="string")):void 0;if(!s){t.status(400).json({ok:!1,error:"agentId is required"});return}const l={action:"install",source:a,...o?{config:o}:{}},m=await g.manage(s,l);t.status(m.ok?200:400).json(m)}));function I(n){return[u,c,p,i(async(t,s)=>{const e=String(t.params.agentId??"").trim(),a=String(t.params.name??"").trim();if(!e||e==="deployed"||!f(a)){s.status(400).json({ok:!1,error:"agentId \u4E14 name \u987B\u4E3A\u5408\u6CD5\u63D2\u4EF6\u540D\uFF08kebab-case\uFF0C1~64 \u5B57\u7B26\uFF09"});return}const o=await g.manage(e,{action:n,name:a});o.ok&&S.onPluginChanged(e,a,n==="uninstall"||n==="disable").catch(()=>{}),s.status(o.ok?200:400).json(o)})]}r.post("/plugins/:agentId/:name/reload",...I("reload")),r.post("/plugins/:agentId/:name/enable",...I("enable")),r.post("/plugins/:agentId/:name/disable",...I("disable")),r.post("/plugins/:agentId/:name/config",u,c,p,i(async(n,t)=>{const s=String(n.params.agentId??"").trim(),e=String(n.params.name??"").trim();if(!s||!f(e)){t.status(400).json({ok:!1,error:"agentId \u4E14 name \u987B\u4E3A\u5408\u6CD5\u63D2\u4EF6\u540D\uFF08kebab-case\uFF0C1~64 \u5B57\u7B26\uFF09"});return}const a=(n.body??{}).config;if(!a||typeof a!="object"||Array.isArray(a)){t.status(400).json({ok:!1,error:"config \u987B\u4E3A JSON \u5BF9\u8C61"});return}const o=await g.updatePluginConfig(s,e,a);t.status(o.ok?200:400).json(o)})),r.delete("/plugins/:agentId/:name",...I("uninstall")),r.get("/plugins/:agentId/:name/logs",u,c,p,i(async(n,t)=>{const s=String(n.params.agentId??"").trim(),e=String(n.params.name??"").trim();if(!s||!f(e)){t.status(400).json({ok:!1,error:"agentId \u4E14 name \u987B\u4E3A\u5408\u6CD5\u63D2\u4EF6\u540D\uFF08kebab-case\uFF0C1~64 \u5B57\u7B26\uFF09"});return}const a=await g.getLogs(s,e);t.status(a.ok?200:404).json(a)})),r.get("/plugins/:agentId/commands",u,c,p,i(async(n,t)=>{const s=String(n.params.agentId??"").trim();if(!s){t.status(400).json({ok:!1,error:"agentId is required"});return}const e=await g.getPluginCommands(s);t.json({ok:!0,agentId:s,commands:e.map(a=>({name:a.name,description:a.description??"",argumentHint:a.argumentHint??"",sourcePath:a.sourcePath,plugin:a.plugin}))})})),r.get("/plugin-events/:agentId/events",y,i(async(n,t)=>{const s=String(n.params.agentId??"").trim();if(!s){t.status(400).json({ok:!1,error:"agentId is required"});return}const e=Number(n.query.maxPerKey),a=Number.isFinite(e)&&e>0?e:void 0,o=await g.drainEvents(s,{maxPerKey:a});t.json({ok:!0,agentId:s,...o})})),r.post("/plugin-events/:agentId/callback/:plugin",y,i(async(n,t)=>{const s=String(n.params.agentId??"").trim(),e=String(n.params.plugin??"").trim(),a=n.body??{};if(!s||!e){t.status(400).json({ok:!1,error:"agentId and plugin are required"});return}const o=await g.enqueueExternalEvent(s,e,a);t.status(o.ok?200:400).json(o)}));const w=new x(g);function h(n){const t=n.query;return{msg_signature:String(t.msg_signature??""),timestamp:String(t.timestamp??""),nonce:String(t.nonce??""),echostr:String(t.echostr??"")}}r.get("/plugins/:agentId/:name/wecom-callback",y,k({type:()=>!0,limit:"64kb"}),i(async(n,t)=>{const s=String(n.params.agentId??"").trim(),e=String(n.params.name??"").trim();if(!s||!f(e)){t.status(400).send("bad request");return}const a=await w.verify(s,h(n),e);t.status(a.status).type("text/plain").send(a.body)})),r.post("/plugins/:agentId/:name/wecom-callback",y,k({type:()=>!0,limit:"64kb"}),i(async(n,t)=>{const s=String(n.params.agentId??"").trim(),e=String(n.params.name??"").trim();if(!s||!f(e)){t.status(400).send("success");return}const a=Buffer.isBuffer(n.body)?n.body.toString("utf8"):String(n.body??""),o=await w.receive(s,h(n),a,e);t.status(o.status).type("text/plain").send(o.body)})),r.post("/plugins/:agentId/private-save",u,c,p,i(async(n,t)=>{const s=String(n.params.agentId??"").trim();if(!s){t.status(400).json({ok:!1,error:"agentId is required"});return}const e=n.body??{},a=Buffer.from(String(e.contentBase64??""),"base64");if(a.length===0){t.status(400).json({ok:!1,error:"contentBase64 \u4E3A\u7A7A"});return}const o=String(e.fileName??"plugin.zip"),l=e.config&&typeof e.config=="object"&&!Array.isArray(e.config)?Object.fromEntries(Object.entries(e.config).filter(d=>typeof d[1]=="string")):void 0,m=await g.installFromZip(s,a,o,l);t.status(m.ok?200:400).json(m)})),r.post("/plugins/:agentId/private-remove",u,c,p,i(async(n,t)=>{const s=String(n.params.agentId??"").trim(),e=String((n.body??{})?.pluginName??"").trim();if(!s||!f(e)){t.status(400).json({ok:!1,error:"agentId \u4E0E pluginName \u5FC5\u586B\uFF08kebab-case\uFF09"});return}const a=await g.manage(s,{action:"uninstall",name:e});t.status(a.ok?200:400).json(a)})),r.post("/plugins/:agentId/upload",u,c,p,k({type:()=>!0,limit:"100mb"}),i(async(n,t)=>{const s=String(n.params.agentId??"").trim();if(!s){t.status(400).json({ok:!1,error:"agentId is required"});return}const e=n.body;if(!Buffer.isBuffer(e)||e.length===0){t.status(400).json({ok:!1,error:"\u7F3A\u5C11 zip \u5185\u5BB9\uFF08raw body, Content-Type: application/zip\uFF09"});return}const a=String(n.query.filename??"plugin.zip");if(!a.toLowerCase().endsWith(".zip")){t.status(400).json({ok:!1,error:"\u4EC5\u652F\u6301 .zip \u63D2\u4EF6\u5305"});return}let o;const l=String(n.query.config??"").trim();if(l)try{const d=JSON.parse(l);if(d&&typeof d=="object"&&!Array.isArray(d))o=Object.fromEntries(Object.entries(d).filter(v=>typeof v[1]=="string"));else{t.status(400).json({ok:!1,error:"config \u5FC5\u987B\u662F JSON \u5BF9\u8C61"});return}}catch{t.status(400).json({ok:!1,error:"config \u4E0D\u662F\u5408\u6CD5\u7684 JSON \u5BF9\u8C61"});return}const m=await g.installFromZip(s,e,a,o);t.status(m.ok?200:400).json(m)}));export{r as pluginsRouter};
|
|
2
2
|
|
|
@@ -55,6 +55,67 @@ export declare function renderSessionSnapshot(messages: Array<{
|
|
|
55
55
|
truncated: boolean;
|
|
56
56
|
};
|
|
57
57
|
|
|
58
|
+
export interface ContextTokenUsage {
|
|
59
|
+
inputTokens: number | null;
|
|
60
|
+
outputTokens: number | null;
|
|
61
|
+
contextLimit: number | null;
|
|
62
|
+
maxOutput: number | null;
|
|
63
|
+
inputLimit: number | null;
|
|
64
|
+
compactionThreshold: number | null;
|
|
65
|
+
totalInputTokens: number | null;
|
|
66
|
+
totalOutputTokens: number | null;
|
|
67
|
+
cacheHitTokens: number | null;
|
|
68
|
+
cacheMissTokens: number | null;
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
type ExportRawTranscriptFn = (sessionId: string) => unknown[] | undefined;
|
|
72
|
+
|
|
73
|
+
type GetConversationFn = (sessionId: string) => unknown[];
|
|
74
|
+
|
|
75
|
+
type GetTotalUsageFn = (sessionId: string) => {
|
|
76
|
+
inputTokens?: number;
|
|
77
|
+
outputTokens?: number;
|
|
78
|
+
contextLimit?: number;
|
|
79
|
+
maxOutput?: number;
|
|
80
|
+
inputLimit?: number;
|
|
81
|
+
compactionThreshold?: number;
|
|
82
|
+
totalInputTokens?: number;
|
|
83
|
+
totalOutputTokens?: number;
|
|
84
|
+
cacheHitTokens?: number;
|
|
85
|
+
cacheMissTokens?: number;
|
|
86
|
+
} | undefined;
|
|
87
|
+
|
|
88
|
+
export interface FullContextPayload {
|
|
89
|
+
ok: true;
|
|
90
|
+
sessionId: string;
|
|
91
|
+
agentId: string;
|
|
92
|
+
workspacePath: string;
|
|
93
|
+
providerId: string;
|
|
94
|
+
format: string;
|
|
95
|
+
messages: unknown[];
|
|
96
|
+
messageCount: number;
|
|
97
|
+
tokenUsage: ContextTokenUsage | null;
|
|
98
|
+
fetchedAt: number;
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
|
|
102
|
+
|
|
103
|
+
|
|
104
|
+
|
|
105
|
+
|
|
106
|
+
|
|
107
|
+
|
|
108
|
+
|
|
109
|
+
export declare function buildFullContextPayload(params: {
|
|
110
|
+
sessionId: string;
|
|
111
|
+
agentId: string;
|
|
112
|
+
workspacePath: string;
|
|
113
|
+
providerId: string;
|
|
114
|
+
exportRawTranscript?: ExportRawTranscriptFn;
|
|
115
|
+
getConversation: GetConversationFn;
|
|
116
|
+
getTotalUsage?: GetTotalUsageFn;
|
|
117
|
+
}): FullContextPayload;
|
|
118
|
+
|
|
58
119
|
|
|
59
120
|
|
|
60
121
|
|
|
@@ -79,6 +140,28 @@ export declare function parseResumeTokenUsage(raw: unknown): AdapterSessionConfi
|
|
|
79
140
|
|
|
80
141
|
export declare const CRASH_RECOVERY_NOTICE_INTERRUPTED: string;
|
|
81
142
|
export declare const CRASH_RECOVERY_NOTICE_CLEAN = "\u6CE8\u610F\uFF1A\u672C\u5B9E\u4F8B\u4E0A\u6B21\u6B63\u5E38\u7ED3\u675F\u8FD0\u884C\u5E76\u81EA\u52A8\u4FDD\u5B58\u4E86\u5B8C\u6574\u8FDB\u5EA6\u3002\u8BF7\u57FA\u4E8E\u5FEB\u7167\u7EE7\u7EED\u63A8\u8FDB\u672A\u5B8C\u6210\u7684\u4E8B\u9879\u3002";
|
|
143
|
+
|
|
144
|
+
|
|
145
|
+
|
|
146
|
+
|
|
147
|
+
|
|
148
|
+
|
|
149
|
+
|
|
150
|
+
|
|
151
|
+
export declare const SDK_WAKE_RESUME_PROMPT = "\u4F11\u7720\u91CD\u65B0\u9192\u6765\uFF0C\u90E8\u5206\u8FD0\u884C\u72B6\u6001\u53EF\u80FD\u5DF2\u4E22\u5931\uFF0C\u8BF7\u7EE7\u7EED\u5DE5\u4F5C\u3002";
|
|
152
|
+
|
|
153
|
+
|
|
154
|
+
|
|
155
|
+
|
|
156
|
+
|
|
157
|
+
|
|
158
|
+
|
|
159
|
+
|
|
160
|
+
export declare function resolveSdkInitialPrompt(initialPrompt: string | undefined, restored: {
|
|
161
|
+
crashRecoveryApplied: boolean;
|
|
162
|
+
resumeTranscriptCount: number;
|
|
163
|
+
resumeContext: string | undefined;
|
|
164
|
+
}): string | undefined;
|
|
82
165
|
export interface RuntimeStopOptions {
|
|
83
166
|
statusNotified: boolean;
|
|
84
167
|
reason: string | undefined;
|