alchemylab 1.0.14 → 1.1.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/478.js +6 -6
- package/dist/60.js +10 -10
- package/dist/800.js +7 -8
- package/dist/cli.js +250 -192
- package/dist/http-server.js +1427 -1732
- package/dist/index.js +1449 -1736
- package/dist/mcp-direct.js +611 -898
- package/dist/plugins/hooks/lib/dedup-utils.js +0 -28
- package/package.json +2 -1
package/dist/mcp-direct.js
CHANGED
|
@@ -34,9 +34,9 @@ let o=(0,s.getErrorMessage)(r),c=""
|
|
|
34
34
|
return r instanceof n.NotFoundError?o=`The request ID "${e.requestId}" was not found. Please provide a valid request ID.`:r instanceof n.ValidationError&&(o.includes("Project cannot accept new tasks")||o.includes("Project is inactive due to tier limits")?c="\n\nThis project is currently inactive due to tier limits. Only your oldest projects can accept new tasks. Please use an active project or upgrade your tier for more simultaneous projects.":o="Invalid input: "+o),a.error("Detailed error when creating task",{error:(0,s.getErrorMessage)(r),stack:r instanceof Error?r.stack:void 0}),i.isOffline,i.apiClient,{content:[{type:"text",text:`Error: ${o}${c}`}],isError:!0}}}
|
|
35
35
|
const r=t(6183),n=t(9860),o=t(2960),s=t(8824)},184(e,exports,t){"use strict"
|
|
36
36
|
function r(e,t,r,n,o={}){const s=u.default.resolve(e)
|
|
37
|
-
if(
|
|
38
|
-
const i=new
|
|
39
|
-
return
|
|
37
|
+
if(O.has(s))return t.child({component:"mcp-server-registry"}).debug("Using existing server for path",{path:s}),O.get(s)
|
|
38
|
+
const i=new j(s,t,r,n,o)
|
|
39
|
+
return O.set(s,i),i}var n,o=this&&this.__createBinding||(Object.create?function(e,t,r,n){void 0===n&&(n=r)
|
|
40
40
|
var o=Object.getOwnPropertyDescriptor(t,r)
|
|
41
41
|
o&&!("get"in o?!t.__esModule:o.writable||o.configurable)||(o={enumerable:!0,get(){return t[r]}}),Object.defineProperty(e,n,o)}:function(e,t,r,n){void 0===n&&(n=r),e[n]=t[r]}),s=this&&this.__setModuleDefault||(Object.create?function(e,t){Object.defineProperty(e,"default",{enumerable:!0,value:t})}:function(e,t){e.default=t}),i=this&&this.__importStar||(n=function(e){return n=Object.getOwnPropertyNames||function(e){var t=[]
|
|
42
42
|
for(var r in e)({}).hasOwnProperty.call(e,r)&&(t[t.length]=r)
|
|
@@ -44,20 +44,20 @@ return t},n(e)},function(e){if(e&&e.__esModule)return e
|
|
|
44
44
|
var t={}
|
|
45
45
|
if(null!=e)for(var r=n(e),i=0;i<r.length;i++)"default"!==r[i]&&o(t,e,r[i])
|
|
46
46
|
return s(t,e),t}),a=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}}
|
|
47
|
-
Object.defineProperty(exports,"__esModule",{value:!0}),exports.McpServer=void 0,exports.resetStdoutWrite=function(){process.stdout.write=
|
|
48
|
-
const c=t(3807),l=t(8909),u=a(t(6928)),d=a(t(9896)),h=a(t(1943)),g=t(9567),p=t(3444),f=t(7660),m=t(1253),y=t(5172),w=
|
|
49
|
-
!(0,p.isDebugToolsEnabled)()||
|
|
50
|
-
class
|
|
47
|
+
Object.defineProperty(exports,"__esModule",{value:!0}),exports.McpServer=void 0,exports.resetStdoutWrite=function(){process.stdout.write=M},exports.getMcpServer=r,exports.createServer=function(e,t,n,o,s={}){return r(e,t,n,o,s)}
|
|
48
|
+
const c=t(3807),l=t(8909),u=a(t(6928)),d=a(t(9896)),h=a(t(1943)),g=t(9567),p=t(3444),f=t(7660),m=t(1253),y=t(5172),w=i(t(7478)),k=t(4139),b=new Set,I=t(9860),v=t(1472),C=t(3328),_=t(8955),E=t(3217),q=t(5278),S=t(446),T=t(9060),R=t(8824),P=(0,p.createLogger)({serviceName:"stdout-capture",console:!1,logToFile:!1}),M=process.stdout.write,x=process.argv.includes("--stdio")||"true"===process.env.MCP_DIRECT_MODE
|
|
49
|
+
!(0,p.isDebugToolsEnabled)()||x&&"true"!==process.env.DEBUG_STDOUT_CAPTURE||(process.stdout.write=function(e){try{return(0,p.isDebugToolsEnabled)()&&"true"===process.env.DEBUG_LOGGING?.toLowerCase()&&"string"==typeof e&&!e.trim().startsWith('{"jsonrpc":"2.0"')&&e.trim().length>0&&P.debug("Stdout output",{content:e.substring(0,100),length:e.length}),M.call(process.stdout,e)}catch(e){return P.error("Error in safeStdoutWrite",{error:e+""}),!0}})
|
|
50
|
+
class j{constructor(e,t,r,n,o={}){this.git=null,this.currentSSEConnection=null,this.stdioTransport=null,this.isInitializing=!1,this.isInitialized=!1,this.logger=t.child({component:"mcp-server"}),this.logger.info("Creating McpServer instance",{basePath:e,remoteServerUrl:n,hasExistingProjectId:!!o.existingProjectId}),this.basePath=e,this.alchemyPath=u.default.join(e,k.ALCHEMY_DIR_NAME),this.metrics=r,this.remoteServerUrl=n,this.existingProjectId=o.existingProjectId,this.gitBinary=(0,l.detectGitBinary)(),this.logger.info("Detected git binary",{gitBinary:this.gitBinary,version:(0,l.getGitVersion)()}),this.projectContext=new f.ProjectContext(e,t),this.tokenManager=new m.TokenManager(t,e,{remoteServerUrl:n}),this.lockOverrideManager=new S.LockOverrideManager(t),this.configManager=new T.ConfigManager(t),this.logger.debug("Server paths initialized",{basePath:this.basePath,alchemyPath:this.alchemyPath}),this.server=new g.Server({name:"alchemy",version:"1.0.0"},{capabilities:{tools:{search:{},create_request:{},complete_task:{},get_task_information:{},complete_request:{},revert_request:{},get_request_information:{},list_tasks:{},list_requests:{},switch_to_branch:{},read_files:{},create_directory:{},move_files:{},write_file:{},replace_strings:{},insert_lines:{},replace_lines:{},delete_files:{},document_operations:{},file_history:{},task_file_history:{},request_file_history:{},quick_write:{},quick_replace:{},quick_manage:{}}}}),(0,y.setGlobalClientInfo)("OpenCode","1.0.0"),this.metrics.incrementCounter("mcp_server_init_started",1),this.logger.info("Starting initialization for server instance"),this.initializationPromise=this.initialize()}get branchState(){if(!this.workspaceManager)return{currentBranch:null,activeRequestId:null,isOnMainBranch:!0}
|
|
51
51
|
const e=this.workspaceManager.getCurrentContext()
|
|
52
52
|
return{currentBranch:e.branchName,activeRequestId:e.requestId,isOnMainBranch:e.isMainBranch}}async updateBranchState(e,t){this.logger.debug("updateBranchState called - managed by WorkspaceManager",{branch:e,requestId:t})}async getCurrentBranchContext(){if(!this.workspaceManager)return{branch:null,requestId:null,isMain:!0}
|
|
53
53
|
const e=this.workspaceManager.getCurrentContext()
|
|
54
54
|
return{branch:e.branchName,requestId:e.requestId,isMain:e.isMainBranch}}async syncBranchState(){this.logger.debug("syncBranchState called - managed by WorkspaceManager")}async switchToMainContext(){return this.workspaceManager?this.workspaceManager.switchToMain():{success:!1,message:"WorkspaceManager not available"}}getCurrentRequestId(){return this.workspaceManager?.getCurrentContext().requestId||null}async getNextId(e){try{const t=this.metrics.startTimer("remote_id_generation"),r=this.apiClient.getProjectClient()
|
|
55
55
|
if(!r||"function"!=typeof r.getNextId)throw Error("Project client or getNextId method not available")
|
|
56
56
|
const n=await r.getNextId(e)
|
|
57
|
-
return t({success:!0,type:e}),this.metrics.incrementCounter("remote_id_success",1,{type:e}),n}catch(t){throw this.metrics.incrementCounter("remote_id_failure",1,{type:e,error:t instanceof Error?t.name:"unknown"}),this.logger.warn("Failed to get ID from remote server, unable to perform operation",{type:e,error:(0,
|
|
57
|
+
return t({success:!0,type:e}),this.metrics.incrementCounter("remote_id_success",1,{type:e}),n}catch(t){throw this.metrics.incrementCounter("remote_id_failure",1,{type:e,error:t instanceof Error?t.name:"unknown"}),this.logger.warn("Failed to get ID from remote server, unable to perform operation",{type:e,error:(0,R.getErrorMessage)(t)}),Error("Failed to get ID from remote server.")}}async initialize(){const e=this.remoteServerUrl||"https://api.alchemylabcode.com"
|
|
58
58
|
this.logger.debug("Using remote server URL",{remoteServerUrl:e})
|
|
59
59
|
const t=u.default.resolve(this.basePath)
|
|
60
|
-
if(
|
|
60
|
+
if(b.has(t))return this.logger.info("Path already initialized in global registry, skipping initialization",{path:t}),void(this.isInitialized=!0)
|
|
61
61
|
if(this.isInitialized)this.logger.info("Server already initialized, skipping initialization")
|
|
62
62
|
else{if(this.isInitializing)return this.logger.info("Initialization already in progress, waiting..."),void await this.initializationPromise
|
|
63
63
|
this.isInitializing=!0,this.logger.info("SERVER INITIALIZATION STARTING",{path:t,pid:process.pid,time:(new Date).toISOString()}),this.metrics.setGauge("mcp_initialization",0,{status:"starting"})
|
|
@@ -65,25 +65,20 @@ try{await this.initializeComplete(),this.isInitialized=!0,this.isInitializing=!1
|
|
|
65
65
|
let t=!1
|
|
66
66
|
try{await h.default.stat(e),this.logger.info("Found existing git repository")}catch{t=!0}this.git=(0,c.simpleGit)({baseDir:this.basePath,binary:this.gitBinary}),t?await this.initializeGitRepo():await this.ensureGitignoreWithAlchemyLab()
|
|
67
67
|
try{this.logger.info("Validating git repository for branch management...")
|
|
68
|
-
const e=await
|
|
68
|
+
const e=await w.validateGitRepository(this.git,this.logger,this.metrics)
|
|
69
69
|
if(e.isGitRepository){this.logger.info("Git repository validation completed",{currentBranch:e.currentBranch,isClean:e.isClean,defaultBranch:e.defaultBranch,branchCount:e.branches.length,hasMainBranch:e.hasMainBranch,hasMasterBranch:e.hasMasterBranch})
|
|
70
70
|
const t=[],r=[]
|
|
71
|
-
e.currentBranch||(t.push("Repository is in detached HEAD state"),r.push("Switch to a proper branch: git checkout main")),e.isClean||(t.push(`Repository has ${e.uncommittedChanges.length} uncommitted changes`),r.push("Commit or stash changes before creating requests")),e.defaultBranch||(t.push("No default branch (main/master) found"),r.push("Create a default branch: git checkout -b main")),t.length>0?this.logger.warn("Git repository has potential issues for branch management",{issues:t,recommendations:r}):this.logger.info("Git repository is ready for automatic branch management"),this.metrics.setGauge("git_repository_ready",0===t.length?1:0),this.metrics.setGauge("git_repository_branch_count",e.branches.length),this.metrics.incrementCounter("git_repository_validation_success",1)}else this.logger.error("Git repository validation failed - not a valid git repository"),this.metrics.incrementCounter("git_repository_validation_failed",1)}catch(e){this.logger.warn("Git repository validation encountered an error",{error:e instanceof Error?e.message:e+""}),this.metrics.incrementCounter("git_repository_validation_error",1)}}async ensureGitignoreWithAlchemyLab(){const e=u.default.join(this.basePath,".gitignore"),t=
|
|
71
|
+
e.currentBranch||(t.push("Repository is in detached HEAD state"),r.push("Switch to a proper branch: git checkout main")),e.isClean||(t.push(`Repository has ${e.uncommittedChanges.length} uncommitted changes`),r.push("Commit or stash changes before creating requests")),e.defaultBranch||(t.push("No default branch (main/master) found"),r.push("Create a default branch: git checkout -b main")),t.length>0?this.logger.warn("Git repository has potential issues for branch management",{issues:t,recommendations:r}):this.logger.info("Git repository is ready for automatic branch management"),this.metrics.setGauge("git_repository_ready",0===t.length?1:0),this.metrics.setGauge("git_repository_branch_count",e.branches.length),this.metrics.incrementCounter("git_repository_validation_success",1)}else this.logger.error("Git repository validation failed - not a valid git repository"),this.metrics.incrementCounter("git_repository_validation_failed",1)}catch(e){this.logger.warn("Git repository validation encountered an error",{error:e instanceof Error?e.message:e+""}),this.metrics.incrementCounter("git_repository_validation_error",1)}}async ensureGitignoreWithAlchemyLab(){const e=u.default.join(this.basePath,".gitignore"),t=k.ALCHEMY_DIR_NAME+"/"
|
|
72
72
|
try{if(d.default.existsSync(e)){const r=await h.default.readFile(e,"utf8")
|
|
73
|
-
if(r.split("\n").some((e=>e.trim()===t||e.trim()===t.slice(0,-1))))this.logger.info(
|
|
73
|
+
if(r.split("\n").some((e=>e.trim()===t||e.trim()===t.slice(0,-1))))this.logger.info(k.ALCHEMY_DIR_NAME+"/ already present in .gitignore")
|
|
74
74
|
else{const n=r.trimEnd()+"\n\n# AlchemyMCP working directory\n"+t+"\n"
|
|
75
|
-
await h.default.writeFile(e,n),this.logger.info(`Added ${
|
|
76
|
-
await h.default.writeFile(e,r),this.logger.info(`Created new .gitignore with ${
|
|
75
|
+
await h.default.writeFile(e,n),this.logger.info(`Added ${k.ALCHEMY_DIR_NAME}/ to existing .gitignore`)}}else{const r=["# Dependency directories\nnode_modules/\n.npm\n.yarn\n\n# Build outputs\ndist/\nbuild/\n\n# Logs\nlogs/\n*.log\n\n# Editor files\n.DS_Store\n.vscode/\n.idea/\n\n# Environment variables\n.env\n.env.local\n\n# AlchemyMCP working directory",t,""].join("\n")
|
|
76
|
+
await h.default.writeFile(e,r),this.logger.info(`Created new .gitignore with ${k.ALCHEMY_DIR_NAME}/ entry`)}}catch(e){this.logger.warn("Failed to update .gitignore file",{error:(0,R.getErrorMessage)(e)})}}async initializeGitRepo(){try{this.logger.info("Initializing git repository"),await this.git.init(),await this.ensureGitignoreWithAlchemyLab()
|
|
77
77
|
const e=u.default.join(this.basePath,"README.md")
|
|
78
78
|
if(!d.default.existsSync(e)){const t=`# Project at ${this.basePath}\n\nCreated with AlchemyMCP Server.\n`
|
|
79
79
|
await h.default.writeFile(e,t)}this.logger.info("Git repository initialized successfully"),await this.git.add(".")
|
|
80
80
|
const t=await this.git.status()
|
|
81
|
-
t.staged.length>0?(await this.git.commit("Initial commit by AlchemyMCP Server"),this.logger.info(`Initial commit created with ${t.staged.length} files`)):this.logger.info("No files to commit in initial repository")}catch(e){this.logger.error("Failed to initialize git repository",{error:e instanceof Error?e.stack:e+""})}}
|
|
82
|
-
this.logger.info("[CLIENT-DEBUG] captureClientInfo called",{hasClientInfo:!!t,clientInfoName:t.name,clientInfoVersion:t.version,initDataKeys:Object.keys(e),userAgent:e.userAgent||t.userAgent,connectionType:this.clientInfo?.connectionType})
|
|
83
|
-
const r=this.detectClientFromName(t.name)
|
|
84
|
-
this.logger.info("[CLIENT-DEBUG] detectClientFromName result",{inputName:t.name,detectedName:r,willUse:r||"Unknown Client"}),this.clientInfo={name:r||"Unknown Client",version:t.version||"Unknown Version",capabilities:e.capabilities||{},userAgent:e.userAgent||t.userAgent,connectedAt:(new Date).toISOString(),initializationData:e},(0,y.setGlobalClientInfo)(this.clientInfo.name||"Unknown Client",this.clientInfo.version||"Unknown Version"),this.logger.info("MCP client connected",{clientName:this.clientInfo.name,clientVersion:this.clientInfo.version,connectionType:this.clientInfo.connectionType||"unknown"})}catch(e){this.logger.error("Failed to capture client information",{error:(0,P.getErrorMessage)(e)})}}detectClientFromName(e){if(!e)return
|
|
85
|
-
const t=e.toLowerCase()
|
|
86
|
-
return"claude-ai"===t||t.includes("claude")?"Claude Desktop":t.includes("vscode")?"VS Code":t.includes("cursor")?"Cursor":t.includes("opencode")?"OpenCode":e}getClientInfo(){return this.clientInfo}cleanupSSEConnection(){this.currentSSEConnection&&(this.currentSSEConnection.transport.close(),this.currentSSEConnection=null,this.logger.debug("SSE connection closed"))}handleError(e,t){if(t instanceof Error){const r=(0,v.createMcpProtocolError)(t.message||"Unknown error")
|
|
81
|
+
t.staged.length>0?(await this.git.commit("Initial commit by AlchemyMCP Server"),this.logger.info(`Initial commit created with ${t.staged.length} files`)):this.logger.info("No files to commit in initial repository")}catch(e){this.logger.error("Failed to initialize git repository",{error:e instanceof Error?e.stack:e+""})}}cleanupSSEConnection(){this.currentSSEConnection&&(this.currentSSEConnection.transport.close(),this.currentSSEConnection=null,this.logger.debug("SSE connection closed"))}handleError(e,t){if(t instanceof Error){const r=(0,I.createMcpProtocolError)(t.message||"Unknown error")
|
|
87
82
|
this.logger.error("MCP error",{message:t.message,name:t.name,stack:t.stack,code:r.code}),e.status(500).json({error:{message:t.message,code:r.code,data:r.data||{details:t.message}}})}else this.logger.error("Unknown error",{error:t+""}),e.status(500).json({error:{message:"Unknown error occurred",code:-32e3,data:{details:t+""}}})
|
|
88
83
|
return Promise.resolve()}async waitForInitialization(){return this.isInitialized?Promise.resolve():(this.logger.debug("Waiting for initialization to complete..."),this.initializationPromise)}async initializeComplete(){let e
|
|
89
84
|
this.logger.info("Starting server initialization")
|
|
@@ -93,8 +88,8 @@ const o=t(6982)
|
|
|
93
88
|
e=`prj_${Date.now().toString().substring(5)}_${o.randomBytes(4).toString("hex")}`,this.logger.warn("Using fallback project ID",{projectId:e,reason:"initialization_failure"})
|
|
94
89
|
try{const t={id:e,name:u.default.basename(this.basePath)||"Local Project",description:"Project for "+u.default.basename(this.basePath),status:"active",createdAt:(new Date).toISOString(),updatedAt:(new Date).toISOString(),metadata:{basePath:this.basePath,alchemyPath:this.alchemyPath,fallback:!0}},r=u.default.join(this.alchemyPath,"project.json")
|
|
95
90
|
d.default.writeFileSync(r,JSON.stringify(t,null,2)),this.logger.debug("Successfully wrote fallback project.json file")}catch(e){this.logger.error("Failed to write fallback project.json",{error:e instanceof Error?e.message:e+""})}}this.logger.info("Server using project ID",{projectId:e})
|
|
96
|
-
const r=this.remoteServerUrl||"https://api.alchemylabcode.com",n=await
|
|
97
|
-
this.apiClient=n,await(0,
|
|
91
|
+
const r=this.remoteServerUrl||"https://api.alchemylabcode.com",n=await C.ClientFactory.createClient(r,this.logger,this.metrics,{workingDir:this.basePath,alchemyPath:this.alchemyPath,tokenManager:this.tokenManager,circuitBreakerThreshold:5,circuitBreakerResetTime:3e4,retryAttempts:3,retryDelay:1e3})
|
|
92
|
+
this.apiClient=n,await(0,_.initializeAgentRegistry)(this.apiClient,this.logger),this.logger.debug("Agent registry initialized"),this.documentFileManager=new q.DocumentFileManager(this.apiClient,this.logger),await this.documentFileManager.initialize(),this.logger.debug("Document file manager initialized"),e&&"PENDING_REMOTE_CREATION"!==e&&(this.apiClient.setProjectId(e),this.logger.debug("Set project ID on API client",{projectId:e}))
|
|
98
93
|
try{const r=this.apiClient.getProjectClient()
|
|
99
94
|
if(this.existingProjectId)this.logger.info("Skipping project synchronization - using existing project from HTTP server",{projectId:e})
|
|
100
95
|
else if("PENDING_REMOTE_CREATION"===e){const{SimpleProjectCreationLock}=await t.e(800).then(t.t.bind(t,3800,23)),n=new SimpleProjectCreationLock(this.basePath,this.logger),o=await n.acquireLock()
|
|
@@ -103,71 +98,34 @@ try{const t=u.default.basename(this.basePath)||"Local Project",n=await r.createP
|
|
|
103
98
|
this.logger.info("Remote project created",{projectId:n.id,name:n.name,processId:process.pid}),await this.projectContext.createProjectFileWithId(n.id,{name:n.name,description:n.description,status:n.status,metadata:{basePath:this.basePath,alchemyPath:this.alchemyPath}}),e=n.id,this.apiClient.setProjectId(e),this.tokenManager.setProjectId(e)}finally{await n.releaseLock()}}else{if(!o.projectData)throw this.logger.error("No project data available from coordination",{processId:process.pid}),Error("Project coordination failed: no project data available")
|
|
104
99
|
this.logger.info("Using project created by another process",{projectId:o.projectData.id,name:o.projectData.name,processId:process.pid}),await this.projectContext.createProjectFileWithId(o.projectData.id,{name:o.projectData.name,description:o.projectData.description,status:o.projectData.status,metadata:{basePath:this.basePath,alchemyPath:this.alchemyPath}}),e=o.projectData.id,this.apiClient.setProjectId(e),this.tokenManager.setProjectId(e)}}else{this.logger.debug("Triggering initial project synchronization..."),await r.syncProjects(),this.logger.debug("Initial project synchronization completed successfully")
|
|
105
100
|
const t=await r.getSynchronizedProjectId()
|
|
106
|
-
t&&t!==e&&(this.logger.info("Project ID changed after synchronization",{oldId:e,newId:t}),e=t,await this.projectContext.updateProjectId(t),this.logger.info("Successfully updated project.json with synchronized ID",{synchronizedProjectId:t}),this.apiClient.setProjectId(t),this.tokenManager.setProjectId(t))}}catch(e){this.logger.warn("Initial project synchronization failed, but continuing initialization",{error:e instanceof Error?e.message:e+""})}await this.initializeGitRepositories(),await this.initializeWorkspaceManager(
|
|
107
|
-
const o=this.getContext();(0,
|
|
108
|
-
const e=await
|
|
109
|
-
return e.isGitRepository?{available:!0,currentBranch:e.currentBranch,isClean:e.isClean,branchCount:e.branches.length,message:`On branch ${e.currentBranch}${e.isClean?" (clean)":" (uncommitted changes)"}`}:{available:!1,message:"Not a git repository"}}catch(e){return this.logger.warn("Failed to get branch info",{error:(0,
|
|
101
|
+
t&&t!==e&&(this.logger.info("Project ID changed after synchronization",{oldId:e,newId:t}),e=t,await this.projectContext.updateProjectId(t),this.logger.info("Successfully updated project.json with synchronized ID",{synchronizedProjectId:t}),this.apiClient.setProjectId(t),this.tokenManager.setProjectId(t))}}catch(e){this.logger.warn("Initial project synchronization failed, but continuing initialization",{error:e instanceof Error?e.message:e+""})}await this.initializeGitRepositories(),await this.initializeWorkspaceManager(),this.logger.info("Re-initializing all tools with full context...")
|
|
102
|
+
const o=this.getContext();(0,v.registerTools)(this.server,o,this.apiClient,this.logger,this.metrics,this.tokenManager,this),this.tokenManager.setProjectId(this.getProjectId()),this.logger.info("Complete initialization finished - all tools available")}async getCurrentBranchInfo(){try{if(!this.git)return{available:!1,message:"No git repository available"}
|
|
103
|
+
const e=await w.getRepositoryStatus(this.git,this.logger,this.metrics)
|
|
104
|
+
return e.isGitRepository?{available:!0,currentBranch:e.currentBranch,isClean:e.isClean,branchCount:e.branches.length,message:`On branch ${e.currentBranch}${e.isClean?" (clean)":" (uncommitted changes)"}`}:{available:!1,message:"Not a git repository"}}catch(e){return this.logger.warn("Failed to get branch info",{error:(0,R.getErrorMessage)(e)}),{available:!1,message:"Git error: "+(0,R.getErrorMessage)(e)}}}async createSseConnection(e,t){await this.waitForInitialization(),this.cleanupSSEConnection(),this.logger.debug("Creating new SSE connection"),e.setHeader("Content-Type","text/event-stream"),e.setHeader("Cache-Control","no-cache"),e.setHeader("Connection","keep-alive")
|
|
110
105
|
const r=new g.SSEServerTransport("/sse",e)
|
|
111
106
|
this.currentSSEConnection={transport:r,response:e}
|
|
112
|
-
try{await this.server.connect(r),this.
|
|
113
|
-
try{await this.server.connect(this.stdioTransport),this.
|
|
114
|
-
"function"==typeof e&&(this.server.connect=async t=>{const r=await e.call(this.server,t)
|
|
115
|
-
return setTimeout((()=>{this.extractClientInfoAfterConnection(),this.searchForClaudeAiPattern()}),500),r})}catch(e){this.logger.error("Failed to intercept connect method",{error:(0,P.getErrorMessage)(e)})}}searchForClaudeAiPattern(){try{const e=this.server,t=(e,r=0)=>{if(r>3||!e||"object"!=typeof e)return!1
|
|
116
|
-
try{for(const[n,o]of Object.entries(e)){if("string"==typeof o&&"claude-ai"===o)return this.captureClientInfo({clientInfo:{name:"claude-ai",version:"0.1.0"}}),!0
|
|
117
|
-
if("object"==typeof o&&null!==o&&t(o,r+1))return!0}}catch(e){}return!1},r=[e._options,e._serverInfo,e._capabilities,this.stdioTransport,this.currentSSEConnection?.transport]
|
|
118
|
-
let n=!1
|
|
119
|
-
for(const e of r)if(e&&t(e)){n=!0
|
|
120
|
-
break}if(!n&&this.clientInfo&&"Unknown Client"===this.clientInfo.name){const e=this.detectClientUsingHeuristics()
|
|
121
|
-
e&&(this.clientInfo.name=e,this.clientInfo.version=this.clientInfo.version||"0.1.0",this.logger.info("Client detected using heuristics",{detectedClient:e,connectionType:this.clientInfo.connectionType,userAgent:this.clientInfo.userAgent}))}}catch(e){this.logger.debug("Error searching for claude-ai pattern",{error:(0,P.getErrorMessage)(e)})}}detectClientUsingHeuristics(){try{if(this.logger.info("[CLIENT-DEBUG] detectClientUsingHeuristics called",{hasClientInfo:!!this.clientInfo,connectionType:this.clientInfo?.connectionType,userAgent:this.clientInfo?.userAgent,currentName:this.clientInfo?.name}),!this.clientInfo)return null
|
|
122
|
-
if("sse"===this.clientInfo.connectionType){const e=this.clientInfo.userAgent?.toLowerCase()||""
|
|
123
|
-
if(this.logger.info("[CLIENT-DEBUG] SSE connection heuristics",{userAgent:e,hasClaude:e.includes("claude"),hasChrome:e.includes("chrome"),hasElectron:e.includes("electron")}),e.includes("claude"))return"Claude Code"
|
|
124
|
-
if(e.includes("chrome")||e.includes("electron"))return"Claude Code"}if("stdio"===this.clientInfo.connectionType){const e=process.env.TERM_PROGRAM?.toLowerCase()||""
|
|
125
|
-
if(e.includes("vscode")||process.env.VSCODE_PID)return"VS Code"
|
|
126
|
-
if(e.includes("cursor")||process.env.CURSOR_PID)return"Cursor"
|
|
127
|
-
if(process.env.CLAUDE_CODE_SESSION||e.includes("claude"))return"Claude Code"
|
|
128
|
-
try{const e=process.ppid
|
|
129
|
-
if(e){const{execSync:r}=t(5317),n=r(`ps -p ${e} -o command=`,{encoding:"utf-8"}).trim(),o=n.toLowerCase()
|
|
130
|
-
if(this.logger.info("[CLIENT-DEBUG] Parent process full command",{parentPid:e,commandLine:n.substring(0,200)}),o.includes("claude-code")||o.includes("@anthropic-ai/claude-code"))return"Claude Code"
|
|
131
|
-
if((o.includes("visual studio code")||o.includes("/code "))&&!o.includes("claude"))return"VS Code"
|
|
132
|
-
if(o.includes("cursor"))return"Cursor"
|
|
133
|
-
if(o.includes("opencode"))return"OpenCode"
|
|
134
|
-
if(o.includes("claude.app")||o.includes("electron")&&o.includes("claude"))return"Claude Desktop"}}catch(e){this.logger.debug("[CLIENT-DEBUG] Parent process detection failed",{error:e instanceof Error?e.message:e+""})}return"Claude Code"}if(this.clientInfo.initializationData){const e=JSON.stringify(this.clientInfo.initializationData).toLowerCase()
|
|
135
|
-
if(e.includes("vscode"))return"VS Code"
|
|
136
|
-
if(e.includes("cursor"))return"Cursor"
|
|
137
|
-
if(e.includes("claude-code"))return"Claude Code"
|
|
138
|
-
if(e.includes("claude")&&e.includes("desktop"))return"Claude Desktop"}return null}catch(e){return this.logger.debug("Error in heuristic client detection",{error:(0,P.getErrorMessage)(e)}),null}}extractClientInfoAfterConnection(){try{setTimeout((()=>{const e=(0,w.getClientInfoForMetadata)(this);(0,y.setGlobalClientInfo)(e.clientName,e.clientVersion)
|
|
139
|
-
const t=(0,y.getGlobalClientInfo)()
|
|
140
|
-
this.logger.info("MCP session initialized with unique session tag",{clientName:e.clientName,clientVersion:e.clientVersion,sessionTag:t.sessionTag,globalInfoSet:{clientName:t.clientName,clientVersion:t.clientVersion,sessionTag:t.sessionTag}})}),100)}catch(e){this.logger.debug("Could not extract client info after connection",{error:(0,P.getErrorMessage)(e)})}}setCurrentSSEConnection(e){this.currentSSEConnection=e}getServer(){return this.server}getCurrentGitInstance(){if(!this.workspaceManager)return this.git||void 0
|
|
107
|
+
try{await this.server.connect(r),this.logger.info("SSE transport connected successfully")}catch(e){this.logger.error("Error connecting SSE transport",{error:(0,R.getErrorMessage)(e)})}return r}async connectStdio(){await this.waitForInitialization(),this.logger.debug("Connecting stdio transport"),this.stdioTransport=new g.StdioServerTransport
|
|
108
|
+
try{await this.server.connect(this.stdioTransport),this.logger.info("STDIO transport connected successfully")}catch(e){this.logger.error("Error connecting stdio transport",{error:(0,R.getErrorMessage)(e)})}}getCurrentSSEConnection(){return this.currentSSEConnection}setCurrentSSEConnection(e){this.currentSSEConnection=e}getServer(){return this.server}getCurrentGitInstance(){if(!this.workspaceManager)return this.git||void 0
|
|
141
109
|
const e=this.workspaceManager.getCurrentContext()
|
|
142
110
|
return"multi-agent"===e.mode&&e.requestId?this.workspaceManager.getCurrentGit():this.git||void 0}getContext(){if(!this.workspaceManager)throw Error("WorkspaceManager not initialized")
|
|
143
|
-
return{mainBasePath:this.basePath,alchemyPath:this.alchemyPath,basePath:this.workspaceManager.getCurrentContext().basePath,projectId:this.getProjectId(),git:this.getCurrentGitInstance(),gitBinary:this.gitBinary,apiClient:this.apiClient,workspaceManager:this.workspaceManager,documentFileManager:this.documentFileManager,lockOverrideManager:this.lockOverrideManager,configManager:this.configManager,getNextId:this.getNextId.bind(this),getCurrentBranchContext:this.getCurrentBranchContext.bind(this),syncBranchState:this.syncBranchState.bind(this),switchToMainContext:this.switchToMainContext.bind(this),getCurrentRequestId:this.getCurrentRequestId.bind(this),updateBranchState:this.updateBranchState.bind(this)
|
|
144
|
-
return t?"req"+t[1]:null}async getEnhancedContext(){return{...this.getContext(),branchInfo:await this.getCurrentBranchInfo()}}getTokenManager(){return this.tokenManager}getProjectId(){try{return this.projectContext.getProjectId()}catch(e){return this.logger.debug("ProjectContext not initialized, using fallback project ID",{error:(0,
|
|
145
|
-
this.workspaceManager=(0,
|
|
146
|
-
throw Error(`Another alchemy instance is running in ${this.basePath}.\n\nTo fix this:\n1. Close the other MCP client/instance\n2. Or if no other instance is running, manually delete the lock file:\n ${e}\n\nNote: Stale locks (>24 hours old) and locks from other computers are automatically cleared.`)}this.logger.info("Process lock acquired for single-agent mode")}async switchToRequestContext(e){return this.logger.debug("switchToRequestContext called",{requestId:e,multiAgentMode:this.multiAgentMode,hasWorkspaceManager:!!this.workspaceManager}),this.multiAgentMode&&this.workspaceManager?this.switchToWorktreeContext(e):this.switchToBranchContext(e)}async switchToWorktreeContext(e){if(this.logger.debug("Using worktree context switching for multi-agent mode",{requestId:e}),!this.workspaceManager)return{success:!1,message:"Workspace manager not available"}
|
|
111
|
+
return{mainBasePath:this.basePath,alchemyPath:this.alchemyPath,basePath:this.workspaceManager.getCurrentContext().basePath,projectId:this.getProjectId(),git:this.getCurrentGitInstance(),gitBinary:this.gitBinary,apiClient:this.apiClient,workspaceManager:this.workspaceManager,documentFileManager:this.documentFileManager,lockOverrideManager:this.lockOverrideManager,configManager:this.configManager,getNextId:this.getNextId.bind(this),getCurrentBranchContext:this.getCurrentBranchContext.bind(this),syncBranchState:this.syncBranchState.bind(this),switchToMainContext:this.switchToMainContext.bind(this),getCurrentRequestId:this.getCurrentRequestId.bind(this),updateBranchState:this.updateBranchState.bind(this)}}isMainBranch(e){return"main"===e||"master"===e}extractRequestIdFromBranch(e){const t=e.match(/^feature\/req(\d+)-/)
|
|
112
|
+
return t?"req"+t[1]:null}async getEnhancedContext(){return{...this.getContext(),branchInfo:await this.getCurrentBranchInfo()}}getTokenManager(){return this.tokenManager}getProjectId(){try{return this.projectContext.getProjectId()}catch(e){return this.logger.debug("ProjectContext not initialized, using fallback project ID",{error:(0,R.getErrorMessage)(e)}),"INITIALIZING"}}generateSessionId(){return`session_${Date.now().toString(36)}_${Math.random().toString(36).substring(2,8)}_${process.pid.toString(36)}`}async getActiveWorktrees(){return await this.workspaceManager.listActiveWorkspaces()}async initializeWorkspaceManager(){try{if(this.logger.debug("initializeWorkspaceManager called",{basePath:this.basePath}),!this.git)throw Error("Git must be initialized before WorkspaceManager")
|
|
113
|
+
this.workspaceManager=(0,E.createWorkspaceManager)(this.basePath,this.logger,this.git,this.metrics,this.apiClient),this.logger.debug("WorkspaceManager created successfully"),this.logger.info("Initialized unified workspace manager",{mode:"multi-agent",basePath:this.basePath})}catch(e){throw this.logger.error("Failed to initialize workspace manager",{error:e}),e}}async switchToRequestContext(e){return this.logger.debug("switchToRequestContext called",{requestId:e,hasWorkspaceManager:!!this.workspaceManager}),this.workspaceManager?this.switchToWorktreeContext(e):{success:!1,message:"Workspace manager not available"}}async switchToWorktreeContext(e){if(this.logger.debug("Using worktree context switching for multi-agent mode",{requestId:e}),!this.workspaceManager)return{success:!1,message:"Workspace manager not available"}
|
|
147
114
|
try{let t="request-"+e
|
|
148
115
|
try{this.logger.debug("Attempting to fetch request title from API",{requestId:e})
|
|
149
116
|
const r=this.apiClient.getRequestClient(),n=await r.getRequest(e)
|
|
150
|
-
n&&n.title?(t=n.title,this.logger.debug("Successfully fetched request title for worktree",{requestId:e,actualTitle:n.title})):this.logger.warn("Request info found but no title, using fallback",{requestId:e,requestInfo:n?"exists":"null",fallbackTitle:t})}catch(r){this.logger.warn("Failed to fetch request title, using fallback",{requestId:e,fallbackTitle:t,error:(0,
|
|
117
|
+
n&&n.title?(t=n.title,this.logger.debug("Successfully fetched request title for worktree",{requestId:e,actualTitle:n.title})):this.logger.warn("Request info found but no title, using fallback",{requestId:e,requestInfo:n?"exists":"null",fallbackTitle:t})}catch(r){this.logger.warn("Failed to fetch request title, using fallback",{requestId:e,fallbackTitle:t,error:(0,R.getErrorMessage)(r),errorStack:r instanceof Error?r.stack:void 0})}const r=this.generateSessionId()
|
|
151
118
|
this.logger.info("Creating worktree for request using WorkspaceManager",{requestId:e,requestTitle:t,sessionId:r}),await this.workspaceManager.ensureWorkspaceReady(e)
|
|
152
119
|
const n=this.workspaceManager.getCurrentContext()
|
|
153
120
|
this.git=(0,c.simpleGit)({baseDir:n.basePath,binary:this.gitBinary})
|
|
154
|
-
try{const t=await
|
|
121
|
+
try{const t=await w.getCurrentBranch(this.git,this.logger,this.metrics)
|
|
155
122
|
if(this.logger.info("Workspace Git instance branch status",{requestId:e,currentBranch:t,expectedBranch:n.branchName,workspacePath:n.basePath,isMainBranch:n.isMainBranch}),t!==n.branchName&&!n.isMainBranch){this.logger.warn("Workspace not on expected branch, attempting to switch",{requestId:e,currentBranch:t,expectedBranch:n.branchName})
|
|
156
|
-
const r=await
|
|
157
|
-
r.success?this.logger.info("Successfully switched workspace to correct branch",{requestId:e,branchName:n.branchName}):this.logger.error("Failed to switch workspace to correct branch",{requestId:e,expectedBranch:n.branchName,error:r.message})}}catch(t){this.logger.error("Failed to verify workspace branch status",{requestId:e,workspacePath:n.basePath,error:t instanceof Error?t.message:t+""})}return this.logger.info("Switched to request context",{requestId:e,workspacePath:n.basePath,branchName:n.branchName}),{success:!0,message:"Switched to workspace for request "+e,worktreePath:n.basePath}}catch(t){const r=(0,
|
|
158
|
-
return this.logger.error("Failed to switch to request context",{requestId:e,error:r}),{success:!1,message:"Failed to switch context: "+r}}}async
|
|
159
|
-
try{let t="request-"+e
|
|
160
|
-
try{const r=this.apiClient.getRequestClient(),n=await r.getRequest(e)
|
|
161
|
-
n&&n.title&&(t=n.title)}catch(t){this.logger.warn("Failed to fetch request title for branch switching",{requestId:e,error:(0,P.getErrorMessage)(t)})}this.logger.info("Ensuring workspace exists before switching (single-agent)",{requestId:e,requestTitle:t,reason:"manual-context-switch"}),await this.workspaceManager.ensureWorkspaceReady(e)
|
|
162
|
-
const r={success:!0,message:"Workspace ready"}
|
|
163
|
-
if(!r.success)return{success:!1,message:r.message||"Failed to switch to request workspace"}
|
|
164
|
-
const n=this.workspaceManager.getCurrentContext()
|
|
165
|
-
this.git=(0,c.simpleGit)({baseDir:n.basePath,binary:this.gitBinary})
|
|
166
|
-
try{const t=await k.getCurrentBranch(this.git,this.logger,this.metrics)
|
|
167
|
-
return this.logger.info("Single-agent Git instance branch status",{requestId:e,currentBranch:t,expectedBranch:n.branchName,basePath:n.basePath}),{success:!0,message:`Switched to request ${e} context`}}catch(t){return this.logger.warn("Branch verification failed but continuing",{requestId:e,error:t instanceof Error?t.message:t+""}),{success:!0,message:`Switched to request ${e} context (branch verification warning)`}}}catch(t){return this.logger.error("Failed to switch to single-agent request context",{requestId:e,error:(0,P.getErrorMessage)(t)}),{success:!1,message:"Failed to switch to request context: "+(0,P.getErrorMessage)(t)}}}async getEffectiveBasePath(e){if(!this.multiAgentMode||!this.workspaceManager||!e)return this.basePath
|
|
123
|
+
const r=await w.switchToBranch(this.git,n.branchName,this.logger,this.metrics)
|
|
124
|
+
r.success?this.logger.info("Successfully switched workspace to correct branch",{requestId:e,branchName:n.branchName}):this.logger.error("Failed to switch workspace to correct branch",{requestId:e,expectedBranch:n.branchName,error:r.message})}}catch(t){this.logger.error("Failed to verify workspace branch status",{requestId:e,workspacePath:n.basePath,error:t instanceof Error?t.message:t+""})}return this.logger.info("Switched to request context",{requestId:e,workspacePath:n.basePath,branchName:n.branchName}),{success:!0,message:"Switched to workspace for request "+e,worktreePath:n.basePath}}catch(t){const r=(0,R.getErrorMessage)(t)
|
|
125
|
+
return this.logger.error("Failed to switch to request context",{requestId:e,error:r}),{success:!1,message:"Failed to switch context: "+r}}}async getEffectiveBasePath(e){if(!this.workspaceManager||!e)return this.basePath
|
|
168
126
|
const t=await this.workspaceManager.getWorkspaceInfo(e)
|
|
169
|
-
return t?.path||this.basePath}}exports.McpServer
|
|
170
|
-
const
|
|
127
|
+
return t?.path||this.basePath}}exports.McpServer=j
|
|
128
|
+
const O=new Map},213(e,exports,t){"use strict"
|
|
171
129
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.def=void 0
|
|
172
130
|
const r=t(6183),n=t(3707)
|
|
173
131
|
exports.def={name:"quick_write",description:"Create or update a file or document. Wraps the change in a request/task workflow that auto-completes.\n\nUse 'path' for filesystem files or 'documentId' for tracked documents.\nSet append:true to add content to existing content.\n\nRequires: title, description, path/documentId, content.",schema:r.QuickWriteSchema,annotations:{title:"Quick Write",readOnlyHint:!1,destructiveHint:!1,idempotentHint:!1},handler(e,t){return(0,n.handleQuickChange)(e,"write",t.context,t.apiClient,t.logger,t.metrics,t.mcpServer)}}},233(e,exports,t){"use strict"
|
|
@@ -238,49 +196,49 @@ default:t="open"}else t="open"
|
|
|
238
196
|
const n=Array.isArray(e.acceptanceCriteria)?e.acceptanceCriteria.map(r):[]
|
|
239
197
|
return{id:e.id,title:e.title,description:e.description,type:e.type,status:t,acceptanceCriteria:n,createdAt:e.createdAt,updatedAt:e.updatedAt,...e.projectId?{projectId:e.projectId}:{},...e.completionSummary?{completionSummary:e.completionSummary}:{},...e.completedAt?{completedAt:e.completedAt}:{},...e.metadata?{metadata:e.metadata}:{},...e.lockInfo?{lockInfo:e.lockInfo}:{}}}Object.defineProperty(exports,"__esModule",{value:!0}),exports.adaptApiAcceptanceCriterionToDomain=r,exports.adaptApiRequestToDomain=n,exports.adaptApiRequestsToDomain=function(e){return e.map(n)}
|
|
240
198
|
const o=t(6756)},355(e,exports,t){"use strict"
|
|
241
|
-
Object.defineProperty(exports,"__esModule",{value:!0}),exports.handleCompleteTask=async function(e,u,d,h
|
|
242
|
-
|
|
243
|
-
const
|
|
244
|
-
try{const{taskId:o,summary:
|
|
199
|
+
Object.defineProperty(exports,"__esModule",{value:!0}),exports.handleCompleteTask=async function(e,l,u,d,h){const g=d.child({tool:"complete_task"})
|
|
200
|
+
g.info("Completing task",{args:e})
|
|
201
|
+
const p=h.startTimer("tool_handler_duration")
|
|
202
|
+
try{const{taskId:o,summary:d}=function(e){if(void 0!==e.verificationSteps){const{verificationSteps:t,...r}=e
|
|
245
203
|
e=r}try{return r.CompleteTaskSchema.parse(e)}catch(e){if(e instanceof i.ZodError&&e.errors.length>0)throw new n.ValidationError(e.errors[0].message)
|
|
246
|
-
throw new n.ValidationError("Invalid input: "+(0,
|
|
247
|
-
if(!
|
|
248
|
-
|
|
249
|
-
const
|
|
250
|
-
let
|
|
251
|
-
try{const e=await
|
|
252
|
-
|
|
253
|
-
const t=(0,s.extractDataFromResponse)(e,{logger:
|
|
254
|
-
|
|
255
|
-
throw new n.NotFoundError(`Task ${o} not found in project ${
|
|
256
|
-
throw
|
|
257
|
-
throw
|
|
258
|
-
try{const e=
|
|
259
|
-
if(r.isLocked){if(r.lockedBySessionTag!==t){let e=`Request ${
|
|
260
|
-
throw r.isExpired?e+="Lock has expired but cleanup may be pending. ":e+=`Lock expires in: ${r.timeRemainingFormatted}. `,e+="Only the agent that locked the request can modify its tasks.",new n.ValidationError(e,{taskId:o,requestId:
|
|
261
|
-
const r=await e.lockRequest(
|
|
262
|
-
if(!r.locked)throw new n.ValidationError(`Failed to acquire lock for request ${
|
|
263
|
-
|
|
264
|
-
throw
|
|
265
|
-
let
|
|
266
|
-
if(
|
|
204
|
+
throw new n.ValidationError("Invalid input: "+(0,c.getErrorMessage)(e))}}(e),f=l.projectId
|
|
205
|
+
if(!f)throw new n.ValidationError("Project ID is required for completing tasks with the new API structure")
|
|
206
|
+
h.incrementCounter("complete_task_attempts",1,{taskId:o}),u.setProjectId(f)
|
|
207
|
+
const m=u.getTaskClient()
|
|
208
|
+
let y
|
|
209
|
+
try{const e=await m.getTask(o)
|
|
210
|
+
g.info("Raw task response data",{responseData:JSON.stringify(e)}),g.debug("Task response structure",{type:typeof e,isArray:Array.isArray(e),hasData:null!=e,properties:e?Object.keys(e):[],dataPreview:e?JSON.stringify(e).substring(0,200)+"...":"null"})
|
|
211
|
+
const t=(0,s.extractDataFromResponse)(e,{logger:g,operationName:"getTask",throwOnNoData:!0})
|
|
212
|
+
y="data"in t?t.data:t,g.info("Current task status: "+y.status,{taskId:o,currentStatus:y.status})}catch(e){if(e instanceof n.ValidationError)throw e
|
|
213
|
+
throw new n.NotFoundError(`Task ${o} not found in project ${f}. Please provide a valid task ID.`,{taskId:o,projectId:f,originalError:e})}if("completed"===y.status){const e="Task is already completed."
|
|
214
|
+
throw g.warn(e,{taskId:o,currentStatus:y.status}),new n.ValidationError(e)}if("canceled"===y.status){const e="Task is canceled and can not be completed."
|
|
215
|
+
throw g.warn(e,{taskId:o,currentStatus:y.status}),new n.ValidationError(e)}if(y.requestId){g.debug("Checking request lock for task operation",{taskId:o,requestId:y.requestId})
|
|
216
|
+
try{const e=u.getRequestClient(),{sessionTag:t}=(0,a.getGlobalClientInfo)(),r=await e.getRequestLockStatus(y.requestId)
|
|
217
|
+
if(r.isLocked){if(r.lockedBySessionTag!==t){let e=`Request ${y.requestId} is locked by another agent (${r.lockedBySessionTag}). `
|
|
218
|
+
throw r.isExpired?e+="Lock has expired but cleanup may be pending. ":e+=`Lock expires in: ${r.timeRemainingFormatted}. `,e+="Only the agent that locked the request can modify its tasks.",new n.ValidationError(e,{taskId:o,requestId:y.requestId,lockedByAgent:r.lockedBySessionTag,currentAgent:t,timeRemainingMs:r.timeRemainingMs,isExpired:r.isExpired})}}else{g.debug("Lock not held, auto-acquiring for task completion",{requestId:y.requestId,sessionTag:t})
|
|
219
|
+
const r=await e.lockRequest(y.requestId,t)
|
|
220
|
+
if(!r.locked)throw new n.ValidationError(`Failed to acquire lock for request ${y.requestId}. Another agent may have just locked it. Try again shortly.`,{taskId:o,requestId:y.requestId})
|
|
221
|
+
g.info("Auto-acquired lock for task completion",{requestId:y.requestId,sessionTag:t,lockedAt:r.lockedAt})}g.info("Request lock validation passed",{taskId:o,requestId:y.requestId,sessionTag:t})}catch(e){if(e instanceof n.ValidationError)throw e
|
|
222
|
+
throw g.error("Failed to check request lock status",{taskId:o,requestId:y.requestId,error:(0,c.getErrorMessage)(e)}),new n.ValidationError("Failed to verify request lock status: "+(0,c.getErrorMessage)(e),{taskId:o,requestId:y.requestId})}}else g.debug("Task without requestId: skipping lock check",{taskId:o,hasRequestId:!!y.requestId})
|
|
223
|
+
let w=l.git
|
|
224
|
+
if(l.workspaceManager){const e=l.workspaceManager.getCurrentContext()
|
|
267
225
|
if("multi-agent"===e.mode&&e.requestId){const{simpleGit}=t(3807)
|
|
268
|
-
|
|
269
|
-
if(
|
|
270
|
-
try{const e=
|
|
271
|
-
e&&(
|
|
272
|
-
|
|
273
|
-
const i=
|
|
274
|
-
let a=`Task ${o} (${
|
|
275
|
-
if(
|
|
276
|
-
|
|
277
|
-
const t=(0,s.extractArrayFromResponse)(e,{logger:
|
|
278
|
-
|
|
226
|
+
w=simpleGit({baseDir:e.basePath,binary:l.gitBinary}),g.debug("Using workspace-aware git instance for task completion",{taskId:o,mode:e.mode,requestId:e.requestId,basePath:e.basePath})}}let k=null
|
|
227
|
+
if(w)try{(await w.status()).isClean()||(k=(await w.commit(`Complete task ${o}: ${d}`)).commit,g.info("Created commit for task completion",{taskId:o,commitId:k}))}catch(e){g.warn("Failed to commit changes",{error:(0,c.getErrorMessage)(e)})}let b=null
|
|
228
|
+
try{const e=u.getToolRecordClient()
|
|
229
|
+
e&&(b={id:(await e.createToolRecord({taskId:o,requestId:y.requestId,projectId:f,type:"complete-task",metadata:{status:"completed",timestamp:(new Date).toISOString(),taskTitle:y.title,completionSummary:d,lastCommit:k,completedAt:(new Date).toISOString()},note:`Completed task: ${d.substring(0,100)}${d.length>100?"...":""}`})).id})}catch(e){g.error("Failed to create tool record for task completion, but continuing",{error:e instanceof Error?e.stack:e+"",taskId:o,requestId:y.requestId})}try{const e=y.metadata||{},t=(new Date).toISOString(),r={status:"completed",metadata:{...e,lastCommit:k,completionSummary:d,completionRecordId:b?.id,completedAt:t}},n=await m.updateTask(o,r)
|
|
230
|
+
g.info("Raw task update response data",{responseData:JSON.stringify(n)}),g.debug("Task update response structure",{type:typeof n,isArray:Array.isArray(n),hasData:null!=n,properties:n?Object.keys(n):[],dataPreview:n?JSON.stringify(n).substring(0,200)+"...":"null"}),(0,s.extractDataFromResponse)(n,{logger:g,operationName:"updateTask",defaultValue:{id:o,status:"completed"}}),g.info("Successfully completed task",{taskId:o,recordId:b?.id})
|
|
231
|
+
const i=y.requestId
|
|
232
|
+
let a=`Task ${o} (${y.title}) has been marked as completed.`
|
|
233
|
+
if(b?.id&&(a+=`\n[RECORD:${b.id}]`),k&&(a+="\nCommit: "+k.substring(0,8)),i)try{const e=await m.listTasks({requestId:i})
|
|
234
|
+
g.info("Raw tasks list response data",{responseData:JSON.stringify(e)}),g.debug("Tasks list response structure",{type:typeof e,isArray:Array.isArray(e),hasData:null!=e,properties:e?Object.keys(e):[],dataPreview:e?JSON.stringify(e).substring(0,200)+"...":"null"})
|
|
235
|
+
const t=(0,s.extractArrayFromResponse)(e,{logger:g,operationName:"listTasksForProgress",defaultValue:[]}),r=t.length,n=t.filter((e=>"completed"===e.status)).length
|
|
236
|
+
g.info("Task progress check",{requestId:i,totalTasks:r,completedTasks:n}),a+=`\n\nTask Progress: ${n}/${r} tasks completed`,n===r&&(a+=`\n\nAll tasks for request ${i} are now completed! You may consider marking the request as completed using the complete-request tool.`)}catch(e){g.warn("Failed to check task progress",{error:(0,c.getErrorMessage)(e),requestId:i})}return p({success:!0}),{content:[{type:"text",text:a}]}}catch(e){throw g.error("Failed to complete task",{error:e instanceof Error?e.stack:e+"",taskId:o}),Error("Failed to complete task: "+(0,c.getErrorMessage)(e))}}catch(t){if(g.error("Failed to complete task",{error:t instanceof Error?t.stack:t+"",args:e}),l.projectId)try{const r=u.getToolRecordClient()
|
|
279
237
|
if(r){const o=t instanceof n.NotFoundError||t instanceof n.ValidationError||t instanceof i.ZodError
|
|
280
|
-
await r.createToolRecord({...o?{}:{taskId:e.taskId},projectId:
|
|
281
|
-
let r=(0,
|
|
238
|
+
await r.createToolRecord({...o?{}:{taskId:e.taskId},projectId:l.projectId,type:"complete-task",metadata:{status:"failed",timestamp:(new Date).toISOString(),taskTitle:e.summary?.substring(0,100)+(e.summary?.length>100?"...":""),error:(0,c.getErrorMessage)(t),errorDetails:t instanceof Error?t.stack:t+"",attemptedTaskId:e.taskId,taskIdValidationFailed:o},note:"Failed to complete task "+e.taskId})}}catch(e){g.error("Failed to create failure record for task completion",{error:e instanceof Error?e.message:e+""})}p({success:!1,error:t instanceof Error?t.name:"unknown"})
|
|
239
|
+
let r=(0,c.getErrorMessage)(t)
|
|
282
240
|
return t instanceof n.NotFoundError&&(r=`The task ID "${e.taskId}" was not found. Please provide a valid task ID.`),t instanceof o.ConnectionError&&(r="Unable to complete task: Connection to the server failed. Please check your network connection and try again."),t instanceof i.ZodError&&t.errors.length>0&&(r=t.errors[0].message),{content:[{type:"text",text:"Error: "+r}],isError:!0}}}
|
|
283
|
-
const r=t(6183),n=t(9860),o=t(5674),s=t(2960),i=t(1569),a=t(5172),c=t(
|
|
241
|
+
const r=t(6183),n=t(9860),o=t(5674),s=t(2960),i=t(1569),a=t(5172),c=t(8824)},405(e,exports,t){"use strict"
|
|
284
242
|
var r,n=this&&this.__createBinding||(Object.create?function(e,t,r,n){void 0===n&&(n=r)
|
|
285
243
|
var o=Object.getOwnPropertyDescriptor(t,r)
|
|
286
244
|
o&&!("get"in o?!t.__esModule:o.writable||o.configurable)||(o={enumerable:!0,get(){return t[r]}}),Object.defineProperty(e,n,o)}:function(e,t,r,n){void 0===n&&(n=r),e[n]=t[r]}),o=this&&this.__setModuleDefault||(Object.create?function(e,t){Object.defineProperty(e,"default",{enumerable:!0,value:t})}:function(e,t){e.default=t}),s=this&&this.__importStar||(r=function(e){return r=Object.getOwnPropertyNames||function(e){var t=[]
|
|
@@ -335,13 +293,16 @@ const n=Date.now(),o=r.createdAt+6e4*r.validityMinutes
|
|
|
335
293
|
return n>o?(this.logger.debug("Password validation failed: expired",{requestId:e,createdAt:new Date(r.createdAt).toISOString(),expiresAt:new Date(o).toISOString(),now:new Date(n).toISOString()}),this.passwords.delete(e),!1):(this.logger.info("Password validation successful",{requestId:e}),this.passwords.delete(e),!0)}cleanupExpiredPasswords(){const e=Date.now()
|
|
336
294
|
let t=0
|
|
337
295
|
for(const[r,n]of this.passwords.entries())e>n.createdAt+6e4*n.validityMinutes&&(this.passwords.delete(r),t++)
|
|
338
|
-
t>0&&this.logger.debug("Cleaned up expired passwords",{count:t})}getActivePasswordCount(){return this.passwords.size}clearAllPasswords(){this.passwords.clear(),this.logger.debug("Cleared all passwords")}destroy(){this.cleanupInterval&&(clearInterval(this.cleanupInterval),this.cleanupInterval=null),this.passwords.clear(),this.logger.debug("Lock override manager destroyed")}}exports.LockOverrideManager=n},
|
|
296
|
+
t>0&&this.logger.debug("Cleaned up expired passwords",{count:t})}getActivePasswordCount(){return this.passwords.size}clearAllPasswords(){this.passwords.clear(),this.logger.debug("Cleared all passwords")}destroy(){this.cleanupInterval&&(clearInterval(this.cleanupInterval),this.cleanupInterval=null),this.passwords.clear(),this.logger.debug("Lock override manager destroyed")}}exports.LockOverrideManager=n},509(e,exports,t){"use strict"
|
|
297
|
+
Object.defineProperty(exports,"__esModule",{value:!0}),exports.def=void 0
|
|
298
|
+
const r=t(6183),n=t(9968)
|
|
299
|
+
exports.def={name:"update_specialization",description:"Update your specialization summary \u2014 a short description of your accumulated domain expertise. Keep it current as you work on different areas.",schema:r.UpdateSpecializationSchema,annotations:{title:"Update Specialization",readOnlyHint:!1,destructiveHint:!1,idempotentHint:!0},handler(e,t){return(0,n.handleUpdateSpecialization)(e,t.logger,t.apiClient??void 0,t.cliOrigin)}}},542(e,exports,t){"use strict"
|
|
339
300
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.debugDefs=void 0
|
|
340
301
|
const r=t(1569),n=t(5997),o=t(8349),s=t(9852),i=t(9422),a=r.z.object({}),c=r.z.object({requestId:r.z.string().optional().describe("Request ID to search for")})
|
|
341
302
|
exports.debugDefs=[{name:"debug_multi_agent_status",description:"Debug tool to check multi-agent mode status, worktree state, and configuration",schema:a,annotations:{title:"Debug Multi-Agent Status",readOnlyHint:!0},debugOnly:!0,readOnly:!0,async handler(e,t){return{content:[{type:"text",text:await(0,n.handleDebugMultiAgentStatus)(e,t.context,t.logger,t.metrics)}]}}},{name:"debug_git_log",description:"Debug tool to examine git log and search for merge commits",schema:a,annotations:{title:"Debug Git Log",readOnlyHint:!0},debugOnly:!0,readOnly:!0,handler(e,t){return(0,o.handleDebugGitLog)(e,t.context,t.logger,t.metrics)}},{name:"debug_git_log_request",description:"Debug tool to examine git log for a specific request",schema:c,annotations:{title:"Debug Git Log Request",readOnlyHint:!0},debugOnly:!0,readOnly:!0,handler(e,t){return(0,s.handleDebugGitLogRequest)(e,t.context,t.logger,t.metrics)}},{name:"debug_request_file_history",description:"Debug tool to test git merge commit search patterns for request file history",schema:c,annotations:{title:"Debug Request File History",readOnlyHint:!0},debugOnly:!0,readOnly:!0,handler(e,t){return(0,i.handleDebugRequestFileHistory)(e,t.context,t.apiClient,t.logger,t.metrics)}}]},700(e,exports,t){"use strict"
|
|
342
303
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.def=void 0
|
|
343
|
-
const r=t(6183),n=t(8037)
|
|
344
|
-
exports.def={name:"list_requests",description
|
|
304
|
+
const r=t(6183),n=t(8037)
|
|
305
|
+
exports.def={name:"list_requests",description:"List requests with filtering options (status, type, dates) and pagination. Shows detailed request information including lock status to indicate which requests are currently in use by other agents.",schema:r.ListRequestsSchema,annotations:{title:"List Requests",readOnlyHint:!0},hidden:!0,readOnly:!0,handler(e,t){return(0,n.handleListRequests)(e,t.context,t.apiClient,t.logger,t.metrics)}}},857(module){"use strict"
|
|
345
306
|
module.exports=require("os")},922(e,exports,t){"use strict"
|
|
346
307
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.ToolRecordClient=void 0
|
|
347
308
|
const r=t(7645),n=t(1038),o=t(2161),s=t(5172),i=t(6688)
|
|
@@ -596,19 +557,19 @@ C=r}else C=t.basePath
|
|
|
596
557
|
I.resolvedPath=C
|
|
597
558
|
let _=!1
|
|
598
559
|
try{_=(await g.default.stat(C)).isFile()}catch(e){const t=`Cannot access path ${C}: ${(0,k.getErrorMessage)(e)}`
|
|
599
|
-
throw I.errors.push(t),Error(t)}const E=v.maxResults||50,q=v.caseSensitive||!1,S=v.useRegex||!1,T=v.fileExtension,
|
|
600
|
-
let
|
|
601
|
-
if(0>
|
|
602
|
-
let
|
|
560
|
+
throw I.errors.push(t),Error(t)}const E=v.maxResults||50,q=v.caseSensitive||!1,S=v.useRegex||!1,T=v.fileExtension,R=v.searchIn||"content"
|
|
561
|
+
let P=void 0!==v.contextLines?v.contextLines:0
|
|
562
|
+
if(0>P?P=0:P>10&&(l.warn(`contextLines ${P} exceeds maximum of 10, clamping to 10`),P=10),!_&&!T)throw I.errors.push('File extension is required for directory search (use "*" for any extension, or formats like "ts", ".ts", "*.ts")'),(0,f.createValidationError)('File extension is required for directory search (use "*" for any extension, or formats like "ts", ".ts", "*.ts")')
|
|
563
|
+
let M,x=""
|
|
603
564
|
if(_)x="*"
|
|
604
565
|
else if("*"===T)x="*"
|
|
605
|
-
else if(T){let e=T;(e.startsWith("*.")||e.startsWith("*"))&&(e=e.substring(1)),x=e.startsWith(".")?e:"."+e}try{
|
|
606
|
-
throw I.errors.push(t),(0,f.createValidationError)(t)}if(I.patternInfo={needle:n,regex:
|
|
566
|
+
else if(T){let e=T;(e.startsWith("*.")||e.startsWith("*"))&&(e=e.substring(1)),x=e.startsWith(".")?e:"."+e}try{M=S?q?RegExp(n):RegExp(n,"i"):q?RegExp(o(n)):RegExp(o(n),"i")}catch(e){const t=`Invalid ${S?"regex":"search"} pattern: ${(0,k.getErrorMessage)(e)}`
|
|
567
|
+
throw I.errors.push(t),(0,f.createValidationError)(t)}if(I.patternInfo={needle:n,regex:M.toString(),caseSensitive:q,fileExtension:T,normalizedExtension:x},!_)try{const e=Date.now(),t=await g.default.readdir(C,{withFileTypes:!0}),r=[],n=[]
|
|
607
568
|
for(const e of t)e.isDirectory()?r.push(e.name):e.isFile()&&n.push(e.name)
|
|
608
569
|
I.initialScan={totalEntries:t.length,directories:r,files:n,firstFewFiles:n.slice(0,10),scanTime:Date.now()-e},I.phases.directoryListingTime=I.initialScan.scanTime}catch(e){const t="Failed to scan directory contents: "+(0,k.getErrorMessage)(e)
|
|
609
|
-
I.errors.push(t),l.error(t)}const
|
|
610
|
-
l.info(`Searching for "${n}" in ${
|
|
611
|
-
const
|
|
570
|
+
I.errors.push(t),l.error(t)}const j=_?"file":"directory"
|
|
571
|
+
l.info(`Searching for "${n}" in ${j} ${C} (mode: ${R})`,{needle:n,searchTarget:j,path:C,options:{maxResults:E,caseSensitive:q,fileExtension:x,searchIn:R}}),b=Date.now(),I.phases.initializationTime=b-d
|
|
572
|
+
const O=Date.now()
|
|
612
573
|
let $=[],D=0,A=0
|
|
613
574
|
try{const e=await async function(e,t,n,o,s,i){const{maxResults:a,fileExtension:c,searchIn:l,isFile:u,contextLines:d}=n,p=[]
|
|
614
575
|
if(s.info("performLocalSearch started",{searchPath:e,pattern:t.toString(),options:n}),u)return await async function(e,t,r,n,o,s=0){const i=[],a=h.default.basename(e)
|
|
@@ -625,17 +586,17 @@ o.errors.push(r),n.error(r)}return{matches:i,totalFiles:1}}(e,t,l,s,i,d)
|
|
|
625
586
|
const f={path:e,filesProcessed:0,filesMatched:0,subdirectories:0,errors:[]}
|
|
626
587
|
try{const{filesCount:n,fileMatchesCount:c,subdirCount:u,subdirStats:h}=await r(e,t,p,a,o,s,0,f,l,d)
|
|
627
588
|
return f.filesProcessed=n,f.filesMatched=c,f.subdirectories=u,i.directoryStats.push(f),h&&h.length>0&&i.directoryStats.push(...h),s.info("performLocalSearch completed",{totalFiles:n,matchesFound:p.length,directories:u+1}),{matches:p,totalFiles:n}}catch(t){const r="Error in performLocalSearch: "+(0,k.getErrorMessage)(t)
|
|
628
|
-
return f.errors.push(r),i.directoryStats.push(f),i.errors.push(r),s.error(r,{error:t instanceof Error?t.stack:t+"",searchPath:e}),{matches:p,totalFiles:f.filesProcessed}}}(C,
|
|
589
|
+
return f.errors.push(r),i.directoryStats.push(f),i.errors.push(r),s.error(r,{error:t instanceof Error?t.stack:t+"",searchPath:e}),{matches:p,totalFiles:f.filesProcessed}}}(C,M,{maxResults:E,fileExtension:x,searchIn:R,isFile:_,contextLines:P},x,l,I)
|
|
629
590
|
$=e.matches,D=e.totalFiles
|
|
630
591
|
const t=1e3
|
|
631
592
|
$.length>0&&$.length<=t?($.sort(((e,t)=>void 0!==e.modifiedTime&&void 0!==t.modifiedTime?t.modifiedTime-e.modifiedTime:void 0!==e.modifiedTime&&void 0===t.modifiedTime?-1:void 0===e.modifiedTime&&void 0!==t.modifiedTime?1:0)),l.info(`Sorted ${$.length} matches by modification time (newest first)`)):$.length>t&&l.info(`Skipped sorting ${$.length} matches (exceeds hard cap of ${t} for performance)`),A=$.length,$.length>E&&($=$.slice(0,E),l.info(`Limited results to ${E} (from ${A} total matches)`)),$.forEach((e=>{e.relativePath=function(e,t){const r=h.default.relative(e,t)
|
|
632
|
-
return r?r===h.default.basename(t)?r:r.startsWith("./")?r.substring(2):r:h.default.basename(t)}(C,e.file)})),l.info(`Local search completed: found ${A||$.length} total matches in ${D} files, returning ${$.length} results`),I.phases.searchTime=Date.now()-
|
|
633
|
-
I.errors.push(t),l.error(t),I.phases.searchTime=Date.now()-
|
|
593
|
+
return r?r===h.default.basename(t)?r:r.startsWith("./")?r.substring(2):r:h.default.basename(t)}(C,e.file)})),l.info(`Local search completed: found ${A||$.length} total matches in ${D} files, returning ${$.length} results`),I.phases.searchTime=Date.now()-O}catch(e){const t="Error during search: "+(0,k.getErrorMessage)(e)
|
|
594
|
+
I.errors.push(t),l.error(t),I.phases.searchTime=Date.now()-O}I.totalFiles=D,I.totalMatches=$.length,I.endTime=Date.now()
|
|
634
595
|
let F,N=""
|
|
635
596
|
try{if(t.getCurrentBranchContext){const e=await t.getCurrentBranchContext()
|
|
636
597
|
e.branch&&(N=e.isMain?` (searched on main branch: ${e.branch})`:` (searched on request branch: ${e.branch}${e.requestId?" for "+e.requestId:""})`)}}catch(e){l.debug("Could not get branch context",{error:e}),N=" (branch context unavailable)"}l.debug("Search diagnostic information",{diagnostic:I})
|
|
637
|
-
const L="content"===
|
|
638
|
-
if(A>$.length?(F=`Found ${A} results for "${n}" (searching ${L})`,p&&(F+=" in "+p),T&&(F+=" with extension "+T),F+=`${N}. Showing first ${$.length}:\n\n`):(F=`Found ${$.length} results for "${n}" (searching ${L})`,p&&(F+=" in "+p),T&&(F+=" with extension "+T),F+=N+":\n\n"),$.length>0)if(
|
|
598
|
+
const L="content"===R?"content":"filename"===R?"filenames":"content and filenames"
|
|
599
|
+
if(A>$.length?(F=`Found ${A} results for "${n}" (searching ${L})`,p&&(F+=" in "+p),T&&(F+=" with extension "+T),F+=`${N}. Showing first ${$.length}:\n\n`):(F=`Found ${$.length} results for "${n}" (searching ${L})`,p&&(F+=" in "+p),T&&(F+=" with extension "+T),F+=N+":\n\n"),$.length>0)if(P>0){const{filenameMatches:e,mergedGroups:t}=function(e,t){const r=e.filter((e=>"filename"===e.matchType)),n=e.filter((e=>"content"===e.matchType))
|
|
639
600
|
if(0===n.length)return{filenameMatches:r,mergedGroups:[]}
|
|
640
601
|
const o=new Map
|
|
641
602
|
for(const e of n){const t=o.get(e.file)||[]
|
|
@@ -643,7 +604,7 @@ t.push(e),o.set(e.file,t)}const i=[]
|
|
|
643
604
|
for(const[e,r]of o.entries()){r.sort(((e,t)=>e.line-t.line))
|
|
644
605
|
let e=[r[0]]
|
|
645
606
|
for(let n=1;n<r.length;n++){const o=e[e.length-1],a=r[n],c=o.line+t
|
|
646
|
-
a.line-t>c+1?(i.push(s(e,t)),e=[a]):e.push(a)}e.length>0&&i.push(s(e,t))}return{filenameMatches:r,mergedGroups:i}}($,
|
|
607
|
+
a.line-t>c+1?(i.push(s(e,t)),e=[a]):e.push(a)}e.length>0&&i.push(s(e,t))}return{filenameMatches:r,mergedGroups:i}}($,P),r=[]
|
|
647
608
|
e.forEach((e=>{r.push(e.relativePath+" [filename match]")})),t.forEach((e=>{const t=[]
|
|
648
609
|
e.lines.forEach((e=>{e.isMatch?t.push(`> ${e.lineNumber}: ${e.content}`):t.push(` ${e.lineNumber}: ${e.content}`)})),r.push(`${e.relativePath}:\n${t.join("\n")}`)})),F+=r.join("\n\n")}else F+=await async function(e){const t=e.filter((e=>"filename"===e.matchType)),r=e.filter((e=>"content"===e.matchType)),n=[]
|
|
649
610
|
t.length>0&&t.forEach((e=>{n.push(e.relativePath+" [filename match]")}))
|
|
@@ -1026,8 +987,8 @@ this.workingDirectory=r.worktreePath,this.logger.info("Using validated worktree
|
|
|
1026
987
|
if(a.default.existsSync(r)){const o=a.default.readFileSync(r,"utf8")
|
|
1027
988
|
this.hasExactConflictMarkers(o)?(t.push(n),this.logger.debug("Found conflict markers in originally conflicted file",{requestId:e,filePath:n,hasStart:/^\s*<{7}(?:\s|$)/m.test(o),hasSeparator:/^\s*={7}(?:\s|$)/m.test(o),hasEnd:/^\s*>{7}(?:\s|$)/m.test(o)})):this.logger.debug("No conflict markers found in file",{requestId:e,filePath:n})}else this.logger.debug("Originally conflicted file no longer exists (possibly deleted as resolution)",{requestId:e,filePath:n})}catch(r){this.logger.warn("Failed to check conflict markers in originally conflicted file",{requestId:e,filePath:n,error:r instanceof Error?r.message:r+""}),a.default.existsSync(i.default.resolve(this.workingDirectory,n))&&t.push(n)}}catch(t){return this.logger.error("Failed to validate conflict markers",{requestId:e,error:(0,n.getErrorMessage)(t)}),{resolved:!1,remainingConflicts:["Failed to validate conflict resolution"]}}return this.logger.info("Conflict marker validation completed",{requestId:e,totalFilesChecked:r?.length||0,filesWithConflicts:t.length,resolved:0===t.length,remainingConflicts:t}),{resolved:0===t.length,remainingConflicts:t}}}exports.ConflictResolutionManager=l},1666(e,exports,t){"use strict"
|
|
1028
989
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.RequestClient=void 0
|
|
1029
|
-
const r=t(7645),n=t(293),o=t(2161),s=t(5172),i=t(
|
|
1030
|
-
class
|
|
990
|
+
const r=t(7645),n=t(293),o=t(2161),s=t(5172),i=t(8824)
|
|
991
|
+
class a extends r.ConnectionAwareClient{constructor(e,t,r,n,o,s,i){const a=t.child({component:"request-client"}),c=s||{isInOfflineMode(){return!1},isOffline(){return!1},setOfflineMode(){},async checkConnectivity(){return!0},getHealthCheckStats(){return{isOffline:!1,consecutiveFailures:0,currentBackoffMs:0,lastCheckTime:0}},cleanup(){}}
|
|
1031
992
|
super(e,a,r,o,i),this.setConnectionStatusManager(c),this.projectClient=n}async createRequest(e){if(!e.title)throw Error("Request title is required")
|
|
1032
993
|
if(!e.type)throw Error("Request type is required")
|
|
1033
994
|
if(!e.description)throw Error("Request description is required")
|
|
@@ -1036,71 +997,69 @@ const t=this.metrics.startTimer("request_creation")
|
|
|
1036
997
|
try{const r=e.projectId||this.projectClient.getProjectId()
|
|
1037
998
|
if(!r)throw this.logger.error("No project ID available for request creation"),Error("No project ID provided or available from project client")
|
|
1038
999
|
this.logger.debug("Token status check",{internalToken:this.authToken?"PRESENT":"MISSING"})
|
|
1039
|
-
let
|
|
1040
|
-
if(!this.isOffline())try{
|
|
1000
|
+
let a=r
|
|
1001
|
+
if(!this.isOffline())try{a=await this.projectClient.ensureProjectExists(r),a!==r&&this.logger.info("Project ID changed during verification",{requestedId:r,actualId:a}),this.logger.debug("Project verified on remote server",{projectId:a})}catch(e){this.logger.warn(`Failed to verify project ${r} on remote server`,{error:(0,i.getErrorMessage)(e)})}let c=[]
|
|
1041
1002
|
Array.isArray(e.acceptanceCriteria)&&e.acceptanceCriteria.length>0&&(c="string"==typeof e.acceptanceCriteria[0]?e.acceptanceCriteria.map(((e,t)=>{const r=null!=e?e:"Acceptance criterion "+(t+1)
|
|
1042
1003
|
return{id:`temp_${Date.now()}_${t}`,description:r,status:"unverified",evidence:null,evidenceType:null}})):e.acceptanceCriteria.map(((e,t)=>{const r="Acceptance criterion "+(t+1)
|
|
1043
1004
|
return{id:e.id||`temp_${Date.now()}_${t}`,description:e.description||e.text||r,status:e.status||(e.verified?"verified":"unverified"),evidence:e.evidence||null,evidenceType:e.evidenceType||null,createdAt:e.createdAt,updatedAt:e.updatedAt}})))
|
|
1044
|
-
const l={title:e.title,description:e.description,type:e.type,acceptanceCriteria:c,projectId:
|
|
1005
|
+
const l={title:e.title,description:e.description,type:e.type,acceptanceCriteria:c,projectId:a}
|
|
1045
1006
|
"status"in e&&e.status?l.status=e.status:l.status="open",e.planDocumentId&&(l.planDocumentId=e.planDocumentId)
|
|
1046
1007
|
const u=(0,s.getGlobalClientInfo)()
|
|
1047
|
-
if(l.clientName=u.clientName,l.clientVersion=u.clientVersion,l.sessionTag=u.sessionTag,this.logger.info("Creating request with client info",{clientName:u.clientName,clientVersion:u.clientVersion,sessionTag:u.sessionTag,requestTitle:e.title}),"metadata"in e&&e.metadata?l.metadata=e.metadata:l.metadata={},e.cliOrigin&&(l.cliOrigin=e.cliOrigin),this.logger.info("Creating request",{title:e.title,type:e.type,projectId:
|
|
1008
|
+
if(l.clientName=u.clientName,l.clientVersion=u.clientVersion,l.sessionTag=u.sessionTag,this.logger.info("Creating request with client info",{clientName:u.clientName,clientVersion:u.clientVersion,sessionTag:u.sessionTag,requestTitle:e.title}),"metadata"in e&&e.metadata?l.metadata=e.metadata:l.metadata={},e.cliOrigin&&(l.cliOrigin=e.cliOrigin),this.logger.info("Creating request",{title:e.title,type:e.type,projectId:a,criteriaCount:c.length}),this.authToken){const e={Authorization:"Bearer "+this.authToken}
|
|
1048
1009
|
this.logger.debug("Auth header prepared for request creation",{tokenLength:this.authToken.length,tokenPrefix:this.authToken.substring(0,10)+"...",tokenSuffix:"..."+this.authToken.substring(this.authToken.length-10)})
|
|
1049
|
-
const r=await this.requestWithRetry("POST",`/api/projects/${
|
|
1010
|
+
const r=await this.requestWithRetry("POST",`/api/projects/${a}/requests`,l,e),s=(0,o.safeGetResponseData)(r,{})
|
|
1050
1011
|
if(!s||!s.id)throw this.logger.error("Received empty response data when creating request"),Error("Failed to create request: Empty response data")
|
|
1051
|
-
return t({success:!0}),this.metrics.incrementCounter("request_creation_success",1),this.logger.info("Successfully created request",{requestId:s.id,title:s.title,type:s.type}),(0,n.adaptApiRequestToDomain)(s)}throw this.logger.error("No authentication token available for request creation"),Error("No authentication token available for request creation")}catch(r){throw t({success:!1}),this.metrics.incrementCounter("request_creation_failure",1),this.logger.error("Failed to create request",{error:(0,
|
|
1012
|
+
return t({success:!0}),this.metrics.incrementCounter("request_creation_success",1),this.logger.info("Successfully created request",{requestId:s.id,title:s.title,type:s.type}),(0,n.adaptApiRequestToDomain)(s)}throw this.logger.error("No authentication token available for request creation"),Error("No authentication token available for request creation")}catch(r){throw t({success:!1}),this.metrics.incrementCounter("request_creation_failure",1),this.logger.error("Failed to create request",{error:(0,i.getErrorMessage)(r),title:e.title,type:e.type}),r}}async getRequests(e,t){const r=e||this.projectClient.getProjectId()
|
|
1052
1013
|
if(!r)throw Error("No project ID provided or available from project client")
|
|
1053
1014
|
this.logger.info("Getting requests for project",{projectId:r,filters:t})
|
|
1054
1015
|
try{const e={}
|
|
1055
|
-
t?.status&&(e.status=t.status),t?.type&&(e.type=t.type),t?.planDocumentId&&(e.planDocumentId=t.planDocumentId),t?.dateFrom&&(e.dateFrom=t.dateFrom),t?.dateTo&&(e.dateTo=t.dateTo),void 0!==t?.limit&&(e.limit=t.limit),void 0!==t?.offset&&(e.offset=t.offset),t?.sortBy&&(e.sortBy="created"===t.sortBy?"created_at":"updated"===t.sortBy?"updated_at":t.sortBy),t?.sortDirection&&(e.sortDirection=t.sortDirection)
|
|
1056
|
-
const s=(0,i.
|
|
1057
|
-
|
|
1058
|
-
const a=await this.requestWithRetry("GET",`/api/projects/${r}/requests`,void 0,void 0,e),c=(0,o.safeGetResponseData)(a,[])
|
|
1059
|
-
return this.logger.info("Successfully retrieved requests",{projectId:r,count:c.length}),(0,n.adaptApiRequestsToDomain)(c)}catch(e){throw this.logger.error("Failed to get requests",{projectId:r,error:(0,a.getErrorMessage)(e)}),e}}async getRequest(e){const t=this.projectClient.getProjectId()
|
|
1016
|
+
t?.status&&(e.status=t.status),t?.type&&(e.type=t.type),t?.planDocumentId&&(e.planDocumentId=t.planDocumentId),t?.dateFrom&&(e.dateFrom=t.dateFrom),t?.dateTo&&(e.dateTo=t.dateTo),void 0!==t?.limit&&(e.limit=t.limit),void 0!==t?.offset&&(e.offset=t.offset),t?.sortBy&&(e.sortBy="created"===t.sortBy?"created_at":"updated"===t.sortBy?"updated_at":t.sortBy),t?.sortDirection&&(e.sortDirection=t.sortDirection),e.includeLockInfo="true",this.logger.info("Requesting lock info from server",{includeLockInfo:e.includeLockInfo,note:"Lock info always requested for operational visibility"}),this.logger.info("Final query parameters to be sent to server",{queryParams:e,projectId:r,url:`/api/projects/${r}/requests`})
|
|
1017
|
+
const s=await this.requestWithRetry("GET",`/api/projects/${r}/requests`,void 0,void 0,e),i=(0,o.safeGetResponseData)(s,[])
|
|
1018
|
+
return this.logger.info("Successfully retrieved requests",{projectId:r,count:i.length}),(0,n.adaptApiRequestsToDomain)(i)}catch(e){throw this.logger.error("Failed to get requests",{projectId:r,error:(0,i.getErrorMessage)(e)}),e}}async getRequest(e){const t=this.projectClient.getProjectId()
|
|
1060
1019
|
if(!t)throw Error("No project ID provided or available from project client")
|
|
1061
1020
|
return this.getRequestWithProject(e,t)}async getRequestWithProject(e,t){this.logger.info("Getting request details",{requestId:e,projectId:t})
|
|
1062
1021
|
try{const r=await this.requestWithRetry("GET",`/api/projects/${t}/requests/${e}`),s=(0,o.safeGetResponseData)(r,{})
|
|
1063
1022
|
if(!s||!s.id)throw Error("Request not found: "+e)
|
|
1064
|
-
return this.logger.info("Successfully retrieved request",{requestId:e,title:s.title,status:s.status}),(0,n.adaptApiRequestToDomain)(s)}catch(r){throw this.logger.error("Failed to get request",{requestId:e,projectId:t,error:(0,
|
|
1023
|
+
return this.logger.info("Successfully retrieved request",{requestId:e,title:s.title,status:s.status}),(0,n.adaptApiRequestToDomain)(s)}catch(r){throw this.logger.error("Failed to get request",{requestId:e,projectId:t,error:(0,i.getErrorMessage)(r)}),r}}async updateRequestStatus(e,t,r){const s=r||this.projectClient.getProjectId()
|
|
1065
1024
|
if(!s)throw Error("No project ID provided or available from project client")
|
|
1066
1025
|
this.logger.info("Updating request status",{requestId:e,status:t,projectId:s})
|
|
1067
1026
|
try{const r=await this.requestWithRetry("PATCH",`/api/projects/${s}/requests/${e}`,{status:t}),i=(0,o.safeGetResponseData)(r,{})
|
|
1068
1027
|
if(!i||!i.id)throw Error("Failed to update request status: "+e)
|
|
1069
|
-
return this.logger.info("Successfully updated request status",{requestId:e,status:i.status}),(0,n.adaptApiRequestToDomain)(i)}catch(r){throw this.logger.error("Failed to update request status",{requestId:e,status:t,projectId:s,error:(0,
|
|
1070
|
-
if(!
|
|
1028
|
+
return this.logger.info("Successfully updated request status",{requestId:e,status:i.status}),(0,n.adaptApiRequestToDomain)(i)}catch(r){throw this.logger.error("Failed to update request status",{requestId:e,status:t,projectId:s,error:(0,i.getErrorMessage)(r)}),r}}async completeRequest(e,t,r,s){const a=s||this.projectClient.getProjectId()
|
|
1029
|
+
if(!a)throw Error("No project ID provided or available from project client")
|
|
1071
1030
|
if(!Array.isArray(t)||0===t.length)throw Error("Evidence is required to complete a request")
|
|
1072
|
-
this.logger.info("Completing request",{requestId:e,projectId:
|
|
1031
|
+
this.logger.info("Completing request",{requestId:e,projectId:a,evidenceCount:t.length})
|
|
1073
1032
|
const c={status:"completed",completionSummary:r,completionEvidences:t}
|
|
1074
|
-
try{const t=await this.requestWithRetry("PATCH",`/api/projects/${
|
|
1033
|
+
try{const t=await this.requestWithRetry("PATCH",`/api/projects/${a}/requests/${e}`,c),s=(0,o.safeGetResponseData)(t,{})
|
|
1075
1034
|
if(!s||!s.id)throw Error("Invalid response when completing request "+e)
|
|
1076
|
-
const
|
|
1077
|
-
return this.logger.info("Successfully completed request",{requestId:e,summary:r.substring(0,50)+(r.length>50?"...":"")}),(0,n.adaptApiRequestToDomain)(
|
|
1035
|
+
const i=s
|
|
1036
|
+
return this.logger.info("Successfully completed request",{requestId:e,summary:r.substring(0,50)+(r.length>50?"...":"")}),(0,n.adaptApiRequestToDomain)(i)}catch(t){throw this.logger.error("Failed to complete request",{requestId:e,projectId:a,error:(0,i.getErrorMessage)(t)}),t}}isOffline(){return!!this.connectionStatusManager&&this.connectionStatusManager.isOffline()}async listRequests(e){const t=this.projectClient.getProjectId()
|
|
1078
1037
|
if(!t)throw Error("No project ID available for listing requests")
|
|
1079
1038
|
const r={}
|
|
1080
1039
|
return e?.status&&(r.status=e.status),e?.type&&(r.type=e.type),e?.planDocumentId&&(r.planDocumentId=e.planDocumentId),e?.dateFrom&&(r.dateFrom=e.dateFrom),e?.dateTo&&(r.dateTo=e.dateTo),void 0!==e?.limit&&(r.limit=+e.limit),void 0!==e?.offset&&(r.offset=+e.offset),e?.sortBy&&(r.sortBy=e.sortBy),e?.sortDirection&&["asc","desc"].includes(e.sortDirection)&&(r.sortDirection=e.sortDirection),this.logger.info("Formatted filters for getRequests",{original:e,formatted:r}),this.getRequests(t,r)}async updateRequest(e,t){const r=this.projectClient.getProjectId()
|
|
1081
1040
|
if(!r)throw Error("No project ID available for updating request")
|
|
1082
1041
|
this.logger.info("Updating request",{requestId:e,projectId:r})
|
|
1083
|
-
const{clientName:n,clientVersion:
|
|
1042
|
+
const{clientName:n,clientVersion:a,sessionTag:c}=(0,s.getGlobalClientInfo)(),l={...t,clientName:n,clientVersion:a,sessionTag:c}
|
|
1084
1043
|
try{const t=await this.requestWithRetry("PATCH",`/api/projects/${r}/requests/${e}`,l),n=(0,o.safeGetResponseData)(t,{})
|
|
1085
1044
|
if(!n||!n.id)throw Error("Invalid response when completing request "+e)
|
|
1086
1045
|
const s=n
|
|
1087
|
-
return this.logger.info("Successfully updated request",{requestId:e,status:s.status}),s}catch(t){throw this.logger.error("Failed to update request",{requestId:e,projectId:r,error:(0,
|
|
1046
|
+
return this.logger.info("Successfully updated request",{requestId:e,status:s.status}),s}catch(t){throw this.logger.error("Failed to update request",{requestId:e,projectId:r,error:(0,i.getErrorMessage)(t)}),t}}async lockRequest(e,t,r){this.logger.debug("Locking request",{requestId:e,sessionTag:t,force:r})
|
|
1088
1047
|
try{const n=this.projectClient.getProjectId()
|
|
1089
1048
|
if(!n)throw Error("Project ID is required for request locking")
|
|
1090
1049
|
const s=await this.requestWithRetry("POST",`/api/projects/${n}/requests/${e}/lock`,{sessionTag:t,force:r}),i=(0,o.safeGetResponseData)(s,{locked:!1,lockedAt:void 0,lockedBySessionTag:void 0},this.logger)
|
|
1091
|
-
return this.logger.info("Request locked successfully",{requestId:e,sessionTag:t,lockedAt:i.lockedAt}),i}catch(r){throw this.logger.error("Failed to lock request",{requestId:e,sessionTag:t,error:(0,
|
|
1050
|
+
return this.logger.info("Request locked successfully",{requestId:e,sessionTag:t,lockedAt:i.lockedAt}),i}catch(r){throw this.logger.error("Failed to lock request",{requestId:e,sessionTag:t,error:(0,i.getErrorMessage)(r)}),r}}async unlockRequest(e,t){this.logger.debug("Unlocking request",{requestId:e,sessionTag:t})
|
|
1092
1051
|
try{const r=this.projectClient.getProjectId()
|
|
1093
1052
|
if(!r)throw Error("Project ID is required for request unlocking")
|
|
1094
1053
|
const n=t?"?sessionTag="+encodeURIComponent(t):"",s=await this.requestWithRetry("DELETE",`/api/projects/${r}/requests/${e}/lock${n}`),i=(0,o.safeGetResponseData)(s,{locked:!0,unlockedAt:void 0},this.logger)
|
|
1095
|
-
return this.logger.info("Request unlocked successfully",{requestId:e,sessionTag:t,unlockedAt:i.unlockedAt}),i}catch(r){throw this.logger.error("Failed to unlock request",{requestId:e,sessionTag:t,error:(0,
|
|
1054
|
+
return this.logger.info("Request unlocked successfully",{requestId:e,sessionTag:t,unlockedAt:i.unlockedAt}),i}catch(r){throw this.logger.error("Failed to unlock request",{requestId:e,sessionTag:t,error:(0,i.getErrorMessage)(r)}),r}}async cleanupExpiredLock(e,t){this.logger.debug("Cleaning up expired lock",{requestId:e,timeoutMinutes:t})
|
|
1096
1055
|
try{const r=this.projectClient.getProjectId()
|
|
1097
1056
|
if(!r)throw Error("Project ID is required for cleaning up expired lock")
|
|
1098
1057
|
const n=t?{timeoutMinutes:t}:{},s=await this.requestWithRetry("POST",`/api/projects/${r}/requests/${e}/cleanup-expired-lock`,n),i=(0,o.safeGetResponseData)(s,{requestId:e,wasCleanedUp:!1,timeoutMinutes:60,cleanedAt:(new Date).toISOString()},this.logger)
|
|
1099
|
-
return this.logger.info("Expired lock cleanup completed",{requestId:e,wasCleanedUp:i.wasCleanedUp,cleanedAt:i.cleanedAt}),{requestId:i.requestId,wasCleanedUp:i.wasCleanedUp,cleanedAt:i.cleanedAt}}catch(r){throw this.logger.error("Failed to clean up expired lock",{requestId:e,timeoutMinutes:t,error:(0,
|
|
1058
|
+
return this.logger.info("Expired lock cleanup completed",{requestId:e,wasCleanedUp:i.wasCleanedUp,cleanedAt:i.cleanedAt}),{requestId:i.requestId,wasCleanedUp:i.wasCleanedUp,cleanedAt:i.cleanedAt}}catch(r){throw this.logger.error("Failed to clean up expired lock",{requestId:e,timeoutMinutes:t,error:(0,i.getErrorMessage)(r)}),r}}async getRequestLockStatus(e){this.logger.debug("Getting request lock status",{requestId:e})
|
|
1100
1059
|
try{const t=this.projectClient.getProjectId()
|
|
1101
1060
|
if(!t)throw Error("Project ID is required for checking request lock status")
|
|
1102
1061
|
const r=await this.requestWithRetry("GET",`/api/projects/${t}/requests/${e}/lock-status`),n=(0,o.safeGetResponseData)(r,{isLocked:!1,lockedAt:void 0,lockedBySessionTag:void 0,timeRemainingMs:0,timeRemainingFormatted:"No lock",isExpired:!0},this.logger)
|
|
1103
|
-
return this.logger.debug("Request lock status retrieved",{requestId:e,isLocked:n.isLocked,lockedBySessionTag:n.lockedBySessionTag,timeRemainingFormatted:n.timeRemainingFormatted,isExpired:n.isExpired}),n}catch(t){throw this.logger.error("Failed to get request lock status",{requestId:e,error:(0,
|
|
1062
|
+
return this.logger.debug("Request lock status retrieved",{requestId:e,isLocked:n.isLocked,lockedBySessionTag:n.lockedBySessionTag,timeRemainingFormatted:n.timeRemainingFormatted,isExpired:n.isExpired}),n}catch(t){throw this.logger.error("Failed to get request lock status",{requestId:e,error:(0,i.getErrorMessage)(t)}),t}}setConnectionStatusManager(e){super.setConnectionStatusManager(e),this.logger.debug("Updated connection status manager in RequestClient")}}exports.RequestClient=a},1695(e,exports,t){"use strict"
|
|
1104
1063
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.HealthCheckManager=void 0
|
|
1105
1064
|
const r=t(8824)
|
|
1106
1065
|
exports.HealthCheckManager=class{constructor(e,t,r,n={}){this.online=!1,this.forcedOfflineMode=!1,this.checkInterval=null,this.lastSuccessTime=0,this.lastFailureTime=0,this.successCount=0,this.failureCount=0,this.consecutiveFailures=0,this.currentBackoffMs=0,this.lastCheckTime=0,this.baseUrl=e,this.logger=t.child({component:"health-check-manager"}),this.metrics=r,this.options={checkIntervalMs:n.checkIntervalMs??3e4,timeoutMs:n.timeoutMs??5e3,retryCount:n.retryCount??2,onOfflineCallback:n.onOfflineCallback??(()=>{}),onOnlineCallback:n.onOnlineCallback??(()=>{})},this.metrics.setGauge("health_check_success_count",0),this.metrics.setGauge("health_check_failure_count",0),this.metrics.setGauge("health_check_last_success",0),this.metrics.setGauge("health_check_last_failure",0)}async performHealthCheck(){const e=Date.now()
|
|
@@ -1115,115 +1074,92 @@ this.forcedOfflineMode=e,t!==e&&(this.logger.info("Offline mode "+(e?"ENABLED":"
|
|
|
1115
1074
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.def=void 0
|
|
1116
1075
|
const r=t(6183),n=t(355)
|
|
1117
1076
|
exports.def={name:"complete_task",description:"Mark a task as completed with a summary of work done.",schema:r.CompleteTaskSchema,annotations:{title:"Complete Task",readOnlyHint:!1,destructiveHint:!1,idempotentHint:!0},handler(e,t){return(0,n.handleCompleteTask)(e,t.context,t.apiClient,t.logger,t.metrics,t.mcpServer)}}},1725(e,exports,t){"use strict"
|
|
1118
|
-
function r(e,t,r){try{const n=`[${(new Date).toISOString()}] ${t}${r?" "+JSON.stringify(r):""}\n`,o=(0,
|
|
1119
|
-
if(
|
|
1120
|
-
const
|
|
1121
|
-
|
|
1122
|
-
if(r(t,"
|
|
1123
|
-
return{content:[{type:"text",text:`\u274c Unknown agent '${a}'.\n\n**Available agents:** ${e.join(", ")}\n\nChoose one of the available agents listed above to see detailed descriptions of each agent.`}],isError:!0}}try{const e=i?.sessionId
|
|
1124
|
-
let n=v.sessionIdentity.getIdentity()?.agentType
|
|
1125
|
-
if(r(t,"Spawn agent type check",{callerSessionId:e||null,cachedAgentType:n||null,pid:process.pid}),!n&&e)try{const o=`http://localhost:${P}/api/sessions/${encodeURIComponent(e)}/agent-type`
|
|
1077
|
+
function r(e,t,r){try{const n=`[${(new Date).toISOString()}] ${t}${r?" "+JSON.stringify(r):""}\n`,o=(0,q.join)(e.basePath||process.cwd(),".alchemy_lab","spawn-debug.log");(0,E.appendFileSync)(o,n)}catch{}}async function n(e,t,n,o,s){const{agent:i="work",prompt:a,requestId:c,allowParallel:l=!1,useExistingSession:u}=e
|
|
1078
|
+
if(r(t,"handleSpawn called",{agent:i,promptLength:a.length,requestId:c,useExistingSession:u,cliOriginSessionId:s?.sessionId||null}),!(0,S.isValidAgent)(i))return{content:[{type:"text",text:`\u274c Unknown agent '${i}'.\n\n**Available agents:** ${(0,S.getAgentNames)().join(", ")}\n\nChoose one of the available agents listed above to see detailed descriptions of each agent.`}],isError:!0}
|
|
1079
|
+
try{const e=s?.sessionId
|
|
1080
|
+
let n=b.sessionIdentity.getIdentity()?.agentType
|
|
1081
|
+
if(r(t,"Spawn agent type check",{callerSessionId:e||null,cachedAgentType:n||null,pid:process.pid}),!n&&e)try{const o=`http://localhost:${T}/api/sessions/${encodeURIComponent(e)}/agent-type`
|
|
1126
1082
|
r(t,"Looking up agent type from action server",{sessionId:e,url:o})
|
|
1127
1083
|
const s=await fetch(o)
|
|
1128
1084
|
if(s.ok){const o=await s.json()
|
|
1129
|
-
r(t,"Agent type response from action server",{sessionId:e,agentType:o.agentType||null,source:o.source||null,success:o.success}),o.success&&o.agentType&&(n=o.agentType,
|
|
1130
|
-
if(e&&!e.includes(
|
|
1131
|
-
try{const e=await
|
|
1132
|
-
if(
|
|
1133
|
-
|
|
1134
|
-
|
|
1135
|
-
|
|
1136
|
-
|
|
1137
|
-
|
|
1138
|
-
|
|
1139
|
-
|
|
1140
|
-
if(
|
|
1141
|
-
|
|
1085
|
+
r(t,"Agent type response from action server",{sessionId:e,agentType:o.agentType||null,source:o.source||null,success:o.success}),o.success&&o.agentType&&(n=o.agentType,b.sessionIdentity.updateIdentity({agentType:n}))}else r(t,"Agent type lookup failed",{sessionId:e,status:s.status})}catch(n){r(t,"Agent type lookup error",{sessionId:e,error:(0,_.getErrorMessage)(n)})}if(n){const e=(0,S.getAllowedSubagents)(n)
|
|
1086
|
+
if(e&&!e.includes(i))return{content:[{type:"text",text:`\u274c Agent type '${n}' cannot spawn '${i}'.\n\n**Allowed subagents for ${n}:** ${e.join(", ")}\n\nUse one of the allowed agent types instead.`}],isError:!0}}}catch(e){r(t,"allowedSubagents check failed",{error:(0,_.getErrorMessage)(e)})}let d
|
|
1087
|
+
try{const e=await async function(e){try{const t=`http://localhost:${T}/api/agents/by-name/${encodeURIComponent(e)}`,r=await fetch(t)
|
|
1088
|
+
if(!r.ok)return null
|
|
1089
|
+
const n=await r.json()
|
|
1090
|
+
return n.success?n.data??null:null}catch{return null}}(i)
|
|
1091
|
+
if(d=e?.requestContextMode,!d){const e=(0,S.getBuiltInAgentConfig)(i)
|
|
1092
|
+
d=e?.requestContextMode}}catch{}if(d&&"none"!==d&&!c)return{content:[{type:"text",text:`\u274c Agent '${i}' requires a requestId to be provided.\n\nThis agent has requestContextMode: '${d}' which means it needs to work in the context of a specific request.\n\nPlease provide a requestId when spawning this agent.`}],isError:!0}
|
|
1093
|
+
const h=await(0,k.getServerUrl)(t,n)
|
|
1094
|
+
r(t,"serverUrl resolved",{serverUrl:h})
|
|
1095
|
+
const g=t.basePath
|
|
1096
|
+
if(!g)throw new y.ValidationError("Working directory not available in context")
|
|
1097
|
+
const p=s?.sessionId
|
|
1098
|
+
let f=""
|
|
1099
|
+
if(o&&c)try{const e=o.getSessionRequestAssociationClient()
|
|
1100
|
+
if(e){const t=await e.getSessionsForRequest(c,!0),r=p?t.filter((e=>e.opencodeSessionId!==p)):t
|
|
1142
1101
|
if(r.length>0){const e=r.map((e=>e.opencodeSessionId)).join(", ")
|
|
1143
|
-
if(!
|
|
1144
|
-
|
|
1145
|
-
|
|
1146
|
-
let
|
|
1147
|
-
if(
|
|
1102
|
+
if(!l)return n.warn("Blocked spawn: request already has active workers",{requestId:c,existingWorkerCount:r.length,existingSessionIds:r.map((e=>e.opencodeSessionId))}),{content:[{type:"text",text:`\u274c Cannot spawn: Request ${c} already has ${r.length} active worker(s): ${e}\n\nOptions:\n\u2022 Use \`useExistingSession: "${r[0].opencodeSessionId}"\` to send work to the existing session\n\u2022 Use \`allowParallel: true\` if you really need multiple workers on the same request`}],isError:!0}
|
|
1103
|
+
f=`\u26a0\ufe0f Warning: Request ${c} already has ${r.length} active worker(s): ${e}. Proceeding anyway (allowParallel=true).\n\n`,n.warn("Spawning parallel subagent for request with existing active workers",{requestId:c,existingWorkerCount:r.length,existingSessionIds:r.map((e=>e.opencodeSessionId)),allowParallel:!0})}}}catch(e){n.debug("Failed to check for existing workers",{error:(0,_.getErrorMessage)(e)})}let m,v,C=a
|
|
1104
|
+
c&&(m="requests/"+c,r(t,"Setting initialBranch for agent",{agent:i,requestId:c,initialBranch:m,agentRequestContextMode:d||"undefined"}),C="readonly"===d?`Working on request ${c} (READONLY mode - you cannot modify files, only explore and report).\n\n${a}`:`Working on request ${c}.\n\n${a}`)
|
|
1105
|
+
let E=!1
|
|
1106
|
+
if(u){if(v=u,n.info("Using existing session for spawn",{sessionId:v,requestId:c}),!h)throw new y.ValidationError("Could not determine OpenCode server URL")
|
|
1148
1107
|
try{let e
|
|
1149
|
-
try{const t=await fetch(`http://localhost:${
|
|
1108
|
+
try{const t=await fetch(`http://localhost:${T}/api/project-settings`)
|
|
1150
1109
|
if(t.ok){const r=await t.json()
|
|
1151
1110
|
if(r.data?.defaultModel){const[t,...n]=r.data.defaultModel.split("/")
|
|
1152
|
-
e={providerID:t,modelID:n.join("/")}}}}catch{}const t=`${
|
|
1111
|
+
e={providerID:t,modelID:n.join("/")}}}}catch{}const t=`${h.replace(/\/$/,"")}/session/${v}/prompt_async`,r=await fetch(t,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({parts:[{type:"text",text:C}],...i?{agent:i}:{},...e?{model:e}:{}}),signal:AbortSignal.timeout(1e4)})
|
|
1153
1112
|
if(!r.ok){const e=await r.text().catch((()=>"Unknown error"))
|
|
1154
|
-
throw Error(`Failed to send to existing session: ${r.status} ${e}`)}
|
|
1155
|
-
const
|
|
1156
|
-
const
|
|
1157
|
-
if(!
|
|
1158
|
-
const
|
|
1159
|
-
if(!
|
|
1160
|
-
const
|
|
1161
|
-
|
|
1162
|
-
const
|
|
1163
|
-
if(!
|
|
1164
|
-
|
|
1165
|
-
|
|
1166
|
-
|
|
1167
|
-
r(t,"Registered child session in DB",{childSessionId:I,childDbId:l.id,parentDbId:o})}catch(e){r(t,"Failed to register sessions in DB",{error:(0,q.getErrorMessage)(e)}),o.warn("Failed to register sessions in alchemy DB",{error:(0,q.getErrorMessage)(e)})}})()
|
|
1168
|
-
let x
|
|
1169
|
-
r(t,"Starting model resolution",{agent:a,cwd:p})
|
|
1170
|
-
try{r(t,"Fetching agent config from action server",{agent:a,url:`http://localhost:${P}/api/agents/by-name/${a}`})
|
|
1171
|
-
const e=await n(a)
|
|
1172
|
-
if(r(t,"Agent config result",{agent:a,agentConfig:e||"null",hasConfig:!!e}),e){const n=e.preferredProvider||"inherit",o=e.preferredModelTier||"same"
|
|
1173
|
-
r(t,"Agent preferences",{agent:a,preferredProvider:n,preferredTier:o,rawProvider:e.preferredProvider,rawTier:e.preferredModelTier})
|
|
1174
|
-
const s=(0,R.resolveAgentModel)(p,n,o)
|
|
1175
|
-
r(t,"Model resolution result",{agent:a,result:s}),s.resolved?(x=s.fullModel,r(t,"Resolved agent model",{agent:a,model:x,preferredProvider:n,preferredTier:o})):r(t,"Model resolution fallback",{agent:a,reason:s.reason})}else{const e=(0,M.getBuiltInAgentConfig)(a)
|
|
1176
|
-
if(r(t,"No API agent config, checking built-in defaults",{agent:a,builtInConfig:e||"null"}),e){const n=e.preferredProvider||"inherit",o=e.preferredModelTier||"same"
|
|
1177
|
-
r(t,"Using built-in agent preferences",{agent:a,preferredProvider:n,preferredTier:o})
|
|
1178
|
-
const s=(0,R.resolveAgentModel)(p,n,o)
|
|
1179
|
-
r(t,"Built-in model resolution result",{agent:a,result:s}),s.resolved&&(x=s.fullModel,r(t,"Resolved built-in agent model",{agent:a,model:x,preferredProvider:n,preferredTier:o}))}else r(t,"No built-in config found - using default model",{agent:a})}}catch(e){r(t,"Error resolving agent model",{agent:a,error:(0,q.getErrorMessage)(e)})}try{const e=await async function(){try{const e=`http://localhost:${P}/api/project-settings`,t=await fetch(e)
|
|
1180
|
-
if(t.ok){const e=await t.json()
|
|
1181
|
-
return e?.data?.defaultModel||null}}catch{}return null}()
|
|
1182
|
-
if(e)if(x){const o=await n(a)
|
|
1183
|
-
"same"===(o?.preferredModelTier||"same")&&(x=e,r(t,"Applied user default model (same tier)",{agent:a,userDefaultModel:e}))}else x=e,r(t,"Using user default model (no agent resolution)",{agent:a,userDefaultModel:e})}catch(e){r(t,"Failed to fetch user default model",{error:(0,q.getErrorMessage)(e)})}if(r(t,"Final resolved model before spawn",{agent:a,resolvedModel:x||"undefined (will use default)"}),await T,l&&y)try{await(0,b.ensureRequestWorktree)(p,l,o)}catch(e){r(t,"Pre-spawn worktree creation failed (non-fatal)",{requestId:l,error:(0,q.getErrorMessage)(e)})}const O=(0,k.spawnDetachedSubagent)({agent:a,prompt:E,cwd:p,sessionId:I,model:x,initialBranch:y,allowParallel:u,serverUrl:g})
|
|
1184
|
-
if(!O.success)throw Error("Failed to spawn subagent: "+O.error)
|
|
1185
|
-
_=I,r(t,"CLI spawn successful with pre-created session",{sessionId:I,pid:O.pid,parentSessionId:i}),o.info("Background subagent spawned via CLI with pre-created session",{agent:a,requestId:l,sessionId:I,pid:O.pid,parentSessionId:i})}if(s&&l&&_&&"unknown"!==_&&"spawning"!==_)try{const e=s.getSessionRequestAssociationClient()
|
|
1186
|
-
if(e&&(e.createAssociation(_,l).then((()=>o.info("Created session-request association",{sessionId:_,requestId:l}))).catch((e=>o.warn("Failed to create session-request association",{error:(0,q.getErrorMessage)(e),sessionId:_,requestId:l}))),"coder"===a)){const e=s.getRequestClient()
|
|
1187
|
-
e&&e.updateRequest(l,{cliOrigin:{providerId:"opencode",sessionId:_,createdAt:(new Date).toISOString()}}).catch((e=>o.debug("Failed to update request cliOrigin",{error:(0,q.getErrorMessage)(e)})))}}catch(e){o.warn("Failed to create session-request association",{error:(0,q.getErrorMessage)(e),sessionId:_,requestId:l})}let T=m
|
|
1188
|
-
return d?T+=`Prompt sent to existing session ${_}.`:(T+=`Background ${a} subagent spawned successfully.`,_&&"unknown"!==_&&"spawning"!==_&&(T+=`\n[SESSION:${_}]`)),l&&(T+="\nWorking on: "+l),T+="\n\nThe subagent is now working independently. You can continue with other tasks.",{content:[{type:"text",text:T}]}}async function s(e,t,r,n,o,s,i){const a=await(0,I.getServerUrl)(r,n)
|
|
1189
|
-
if(!a)throw new w.ValidationError("Could not determine OpenCode server URL")
|
|
1113
|
+
throw Error(`Failed to send to existing session: ${r.status} ${e}`)}n.info("Prompt sent to existing session",{sessionId:v,agent:i})}catch(e){throw Error("Failed to use existing session: "+(0,_.getErrorMessage)(e))}}else{E=!0,r(t,"Creating session via spawn-session endpoint")
|
|
1114
|
+
const o=p;(0,I.logSessionIdentity)("subagent_operations.spawn","_meta",{parentSessionId:o})
|
|
1115
|
+
try{const s=`http://localhost:${T}/api/spawn-session`,u=await fetch(s,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({agent:i,prompt:a,requestId:c,parentSessionId:o,title:e.title,specialization:e.specialization,allowParallel:l,callerAgentType:b.sessionIdentity.getIdentity()?.agentType}),signal:AbortSignal.timeout(15e3)})
|
|
1116
|
+
if(!u.ok){const e=await u.text().catch((()=>"Unknown error"))
|
|
1117
|
+
throw Error(`Spawn session endpoint failed: ${u.status} ${e}`)}const d=await u.json()
|
|
1118
|
+
if(!d.success||!d.data)throw Error(d.error||"Spawn session returned unsuccessful")
|
|
1119
|
+
const{sessionId:h,model:p,serverUrl:f,initialBranch:y}=d.data
|
|
1120
|
+
m=y
|
|
1121
|
+
const k=(0,w.spawnDetachedSubagent)({agent:i,prompt:C,cwd:g,sessionId:h,model:p,initialBranch:m,allowParallel:l,serverUrl:f})
|
|
1122
|
+
if(!k.success)throw Error("Failed to spawn subagent: "+k.error)
|
|
1123
|
+
v=h,r(t,"Spawn successful via unified endpoint",{sessionId:h,pid:k.pid,parentSessionId:o,model:p}),n.info("Background subagent spawned via unified endpoint",{agent:i,requestId:c,sessionId:h,pid:k.pid,parentSessionId:o})}catch(e){throw Error("Failed to spawn subagent: "+(0,_.getErrorMessage)(e))}}let q=f
|
|
1124
|
+
return u?q+=`Prompt sent to existing session ${v}.`:(q+=`Background ${i} subagent spawned successfully.`,v&&"unknown"!==v&&"spawning"!==v&&(q+=`\n[SESSION:${v}]`)),c&&(q+="\nWorking on: "+c),q+="\n\nThe subagent is now working independently. You can continue with other tasks.","coder"===i&&(q+="\n\nIf this work has shifted or expanded your area of expertise, update your specialization summary with `update_specialization`."),{content:[{type:"text",text:q}]}}async function o(e,t,r,n,o,s,i){const a=await(0,k.getServerUrl)(r,n)
|
|
1125
|
+
if(!a)throw new y.ValidationError("Could not determine OpenCode server URL")
|
|
1190
1126
|
if(n.info("Sending message to subagent session",{sessionId:e,promptLength:t.length}),o)try{const t=i?.sessionId
|
|
1191
1127
|
if(t){const r=o.getCLISessionClient()
|
|
1192
1128
|
if(r){let o=await r.getByExternalId(t)
|
|
1193
|
-
o||(o=await r.createOrUpdateSession({externalSessionId:t,providerId:"opencode",status:"active"}),n.info("Created caller session in DB for re-parenting",{callerSessionId:t,dbId:o?.id})),o&&(await r.createOrUpdateSession({externalSessionId:e,providerId:"opencode",parentSessionId:o.id,status:"active"}),n.info("Updated parent session for reused agent",{sessionId:e,newParentSessionId:t}))}}}catch(e){n.warn("Failed to update parent session - reports may go to wrong parent",{error:(0,
|
|
1194
|
-
if(!c)try{const t=`http://localhost:${
|
|
1129
|
+
o||(o=await r.createOrUpdateSession({externalSessionId:t,providerId:"opencode",status:"active"}),n.info("Created caller session in DB for re-parenting",{callerSessionId:t,dbId:o?.id})),o&&(await r.createOrUpdateSession({externalSessionId:e,providerId:"opencode",parentSessionId:o.id,status:"active"}),n.info("Updated parent session for reused agent",{sessionId:e,newParentSessionId:t}))}}}catch(e){n.warn("Failed to update parent session - reports may go to wrong parent",{error:(0,_.getErrorMessage)(e)})}let c=s
|
|
1130
|
+
if(!c)try{const t=`http://localhost:${T}/api/sessions/${encodeURIComponent(e)}/agent-type`,r=await fetch(t)
|
|
1195
1131
|
if(r.ok){const e=await r.json()
|
|
1196
|
-
e.success&&e.agentType&&(c=e.agentType)}}catch{n.warn("Agent type lookup failed for session",{sessionId:e})}if(!c)throw new
|
|
1132
|
+
e.success&&e.agentType&&(c=e.agentType)}}catch{n.warn("Agent type lookup failed for session",{sessionId:e})}if(!c)throw new y.ValidationError(`Cannot continue session ${e}: unable to determine agent type. The session's agent type could not be looked up from the action server.`)
|
|
1197
1133
|
try{let r
|
|
1198
|
-
try{const e=await fetch(`http://localhost:${
|
|
1134
|
+
try{const e=await fetch(`http://localhost:${T}/api/project-settings`)
|
|
1199
1135
|
if(e.ok){const t=await e.json()
|
|
1200
1136
|
if(t.data?.defaultModel){const[e,...n]=t.data.defaultModel.split("/")
|
|
1201
1137
|
r={providerID:e,modelID:n.join("/")}}}}catch{}const o=`${a.replace(/\/$/,"")}/session/${e}/prompt_async`,s=await fetch(o,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({parts:[{type:"text",text:t}],...c?{agent:c}:{},...r?{model:r}:{}}),signal:AbortSignal.timeout(1e4)})
|
|
1202
1138
|
if(!s.ok){const e=await s.text().catch((()=>"Unknown error"))
|
|
1203
|
-
throw Error(`Failed to send message: ${s.status} ${e}`)}return n.info("Message sent to subagent session",{sessionId:e,agent:c}),{content:[{type:"text",text:`Message sent to session ${e}.\nThe subagent will process it in the background.`}]}}catch(e){throw Error("Failed to continue session: "+(0,
|
|
1139
|
+
throw Error(`Failed to send message: ${s.status} ${e}`)}return n.info("Message sent to subagent session",{sessionId:e,agent:c}),{content:[{type:"text",text:`Message sent to session ${e}.\nThe subagent will process it in the background.`}]}}catch(e){throw Error("Failed to continue session: "+(0,_.getErrorMessage)(e))}}function s(e){const t=Math.floor(e/1e3)
|
|
1204
1140
|
if(60>t)return t+"s"
|
|
1205
1141
|
const r=Math.floor(t/60)
|
|
1206
|
-
return 60>r?`${r}m ${t%60}s`:`${Math.floor(r/60)}h ${r%60}m`}function
|
|
1142
|
+
return 60>r?`${r}m ${t%60}s`:`${Math.floor(r/60)}h ${r%60}m`}function i(e){const t=[]
|
|
1207
1143
|
for(const r of e)if("assistant"===r.info.role&&r.parts)for(const e of r.parts)if("tool"===e.type&&e.tool&&e.state){const n=e.state.input||{}
|
|
1208
1144
|
let o=e.tool
|
|
1209
1145
|
const s=n.path||n.file||n.directory,i=n.needle||n.query||n.pattern
|
|
1210
1146
|
"string"==typeof s?o+=" "+(s.split("/").pop()||s):"string"==typeof i&&(o+=` "${i.length>30?i.slice(0,27)+"...":i}"`),t.push({name:o,state:e.state.status,time:r.info.time.created})}t.sort(((e,t)=>t.time-e.time))
|
|
1211
1147
|
const r=t.find((e=>"pending"===e.state||"running"===e.state)),n=t.filter((e=>"completed"===e.state||"error"===e.state)).slice(0,3),o=t.length>0?t[0].time:null
|
|
1212
|
-
return{current:r?.name??null,recent:n.map((e=>e.name)),lastActivityTime:o}}function
|
|
1213
|
-
return e&&
|
|
1148
|
+
return{current:r?.name??null,recent:n.map((e=>e.name)),lastActivityTime:o}}function a(e){return 1e3>e?"<1s ago":6e4>e?Math.floor(e/1e3)+"s ago":36e5>e?Math.floor(e/6e4)+"m ago":Math.floor(e/36e5)+"h ago"}function c(e,t){const r=e||t,n=Date.now()-r
|
|
1149
|
+
return e&&R>n?{status:"working",detail:"last action "+a(n),isReady:!1}:n>P&&e?{status:"stalled",detail:"no activity for "+a(n),isReady:!0}:e?{status:"idle",detail:"no activity for "+a(n),isReady:!0}:{status:"idle",detail:"no tool activity",isReady:!0}}function l(e){let t=0,r=0,n=0
|
|
1214
1150
|
for(const o of e.trim().split("\n")){if(!o)continue
|
|
1215
1151
|
const[e,s]=o.split("\t")
|
|
1216
|
-
"-"!==e&&(t+=parseInt(e,10)||0),"-"!==s&&(r+=parseInt(s,10)||0),n++}return{additions:t,deletions:r,files:n}}async function
|
|
1217
|
-
if(!
|
|
1152
|
+
"-"!==e&&(t+=parseInt(e,10)||0),"-"!==s&&(r+=parseInt(s,10)||0),n++}return{additions:t,deletions:r,files:n}}async function u(e,r,n,o){const a=await(0,k.getServerUrl)(r,n)
|
|
1153
|
+
if(!a)throw new y.ValidationError("Could not determine OpenCode server URL")
|
|
1218
1154
|
n.info("Checking status of subagent session",{sessionId:e})
|
|
1219
|
-
try{const
|
|
1155
|
+
try{const u=`${a.replace(/\/$/,"")}/session/${e}`,d=await fetch(u)
|
|
1220
1156
|
if(!d.ok)return{content:[{type:"text",text:`Session ${e} not found or has exited.`}],isError:!0}
|
|
1221
|
-
const h=await d.json(),g=`${
|
|
1222
|
-
let f={input:0,output:0,reasoning:0},m="",y=
|
|
1157
|
+
const h=await d.json(),g=`${a.replace(/\/$/,"")}/session/${e}/message`,p=await fetch(g)
|
|
1158
|
+
let f={input:0,output:0,reasoning:0},m="",y=c(null,h.time.updated)
|
|
1223
1159
|
if(p.ok){const e=await p.json()
|
|
1224
1160
|
for(const t of e)"assistant"===t.info.role&&t.info.tokens&&(f.input+=t.info.tokens.input||0,f.output+=t.info.tokens.output||0,f.reasoning+=t.info.tokens.reasoning||0)
|
|
1225
|
-
const t=
|
|
1226
|
-
y=
|
|
1161
|
+
const t=i(e)
|
|
1162
|
+
y=c(t.lastActivityTime,h.time.updated),t.current&&(m+="\nCurrent: "+t.current),t.recent.length>0&&(m+="\nRecent: "+t.recent.join(", "))}const w=Date.now()-h.time.created,k=y.status,b=y.isReady,I=f.input+f.output+f.reasoning
|
|
1227
1163
|
let v="",C="",_=null
|
|
1228
1164
|
if(o)try{const t=o.getSessionRequestAssociationClient()
|
|
1229
1165
|
if(t){const r=await t.getActiveRequestsForSession(e,!1)
|
|
@@ -1234,74 +1170,87 @@ t.length>0&&a.push("Active: "+t.map((e=>e.requestLocalId)).join(", ")),o.length>
|
|
|
1234
1170
|
return t?t[1]:null}(h.title||"")),_&&r.basePath){const e=await async function(e,r){try{const{execSync:n}=await Promise.resolve().then(t.t.bind(t,5317,23)),o="requests/"+e
|
|
1235
1171
|
let s=!1
|
|
1236
1172
|
try{n("git rev-parse --verify "+o,{cwd:r,stdio:"pipe"}),s=!0}catch{s=!1}if(s){const e=n(`git diff main...${o} --numstat`,{cwd:r,encoding:"utf8"})
|
|
1237
|
-
if(e.trim())return
|
|
1173
|
+
if(e.trim())return l(e)}try{const t=n(`git log main --merges --oneline -n 50 --grep="${e}"`,{cwd:r,encoding:"utf8"}).trim()
|
|
1238
1174
|
if(t){const e=t.split("\n")[0].split(" ")[0],o=n(`git diff ${e}^1...${e} --numstat`,{cwd:r,encoding:"utf8"})
|
|
1239
|
-
if(o.trim())return{...
|
|
1175
|
+
if(o.trim())return{...l(o),merged:!0}}}catch{}return null}catch{return null}}(_,r.basePath)
|
|
1240
1176
|
if(e){const t=e.additions+e.deletions,r=e.merged?" (merged)":""
|
|
1241
|
-
v=`\nDiff vs main (${_}): +${e.additions}/-${e.deletions} lines (${t} total) in ${e.files} file${1!==e.files?"s":""}${r}`}}return{content:[{type:"text",text:`Session ${e}\nTitle: ${h.title||"Untitled"}\nStatus: ${k} (${y.detail})\nReady for input: ${b?"Yes":"No"}\nAge: ${
|
|
1242
|
-
if(!n)throw new
|
|
1177
|
+
v=`\nDiff vs main (${_}): +${e.additions}/-${e.deletions} lines (${t} total) in ${e.files} file${1!==e.files?"s":""}${r}`}}return{content:[{type:"text",text:`Session ${e}\nTitle: ${h.title||"Untitled"}\nStatus: ${k} (${y.detail})\nReady for input: ${b?"Yes":"No"}\nAge: ${s(w)}\nTokens: ${I.toLocaleString()} (in: ${f.input.toLocaleString()}, out: ${f.output.toLocaleString()}${f.reasoning>0?", reasoning: "+f.reasoning.toLocaleString():""})${m}${C}${v}`}]}}catch(e){throw Error("Failed to check session status: "+(0,_.getErrorMessage)(e))}}async function d(e,t,r){const n=await(0,k.getServerUrl)(t,r)
|
|
1178
|
+
if(!n)throw new y.ValidationError("Could not determine OpenCode server URL")
|
|
1243
1179
|
r.info("Aborting subagent session",{sessionId:e})
|
|
1244
1180
|
try{const t=`${n.replace(/\/$/,"")}/session/${e}/abort`,o=await fetch(t,{method:"POST"})
|
|
1245
1181
|
if(!o.ok){const e=await o.text().catch((()=>"Unknown error"))
|
|
1246
|
-
throw Error(`Failed to abort session: ${o.status} ${e}`)}return r.info("Session aborted",{sessionId:e}),{content:[{type:"text",text:`Session ${e} has been aborted.`}]}}catch(e){throw Error("Failed to abort session: "+(0,
|
|
1247
|
-
if(!g)throw new
|
|
1182
|
+
throw Error(`Failed to abort session: ${o.status} ${e}`)}return r.info("Session aborted",{sessionId:e}),{content:[{type:"text",text:`Session ${e} has been aborted.`}]}}catch(e){throw Error("Failed to abort session: "+(0,_.getErrorMessage)(e))}}async function h(e,t,r,n={}){const{activeOnly:o=!1,requestId:a,limit:l,minTokens:u,maxTokens:d,maxAgeHours:h}=n,g=await(0,k.getServerUrl)(e,t)
|
|
1183
|
+
if(!g)throw new y.ValidationError("Could not determine OpenCode server URL")
|
|
1248
1184
|
t.info("Listing sessions",{filters:n})
|
|
1249
1185
|
try{const e=g.replace(/\/$/,"")+"/session",t=await fetch(e)
|
|
1250
1186
|
if(!t.ok)throw Error("Failed to fetch sessions: "+t.status)
|
|
1251
1187
|
let p=await t.json()
|
|
1252
1188
|
if(0===p.length)return{content:[{type:"text",text:"No sessions found."}]}
|
|
1189
|
+
const f=p
|
|
1253
1190
|
n.parentSessionId&&(p=p.filter((e=>(e.parentId||e.parentID)===n.parentSessionId))),p.sort(((e,t)=>t.time.created-e.time.created))
|
|
1254
|
-
const
|
|
1255
|
-
let
|
|
1256
|
-
if(o&&(
|
|
1257
|
-
|
|
1258
|
-
let
|
|
1259
|
-
|
|
1260
|
-
|
|
1261
|
-
|
|
1262
|
-
|
|
1263
|
-
|
|
1191
|
+
const m=g.replace(/\/$/,"")+"/session/status",y=await fetch(m),w=y.ok?await y.json():{}
|
|
1192
|
+
let k=p
|
|
1193
|
+
if(o&&(k=k.filter((e=>"idle"!==(w[e.id]?.type||"idle")))),void 0!==h){const e=36e5*h,t=Date.now()-e
|
|
1194
|
+
k=k.filter((e=>e.time.created>=t))}if(0===k.length)return{content:[{type:"text",text:"No sessions match the specified filters."}]}
|
|
1195
|
+
let b={}
|
|
1196
|
+
const I=k.map((e=>e.id))
|
|
1197
|
+
let v={},C=[]
|
|
1198
|
+
if("specialist"===n.agentType){const e=new Set(I)
|
|
1199
|
+
for(const t of f){const r=t.parentId||t.parentID
|
|
1200
|
+
r&&e.has(r)&&(v[r]||(v[r]=[]),v[r].push(t.id),C.push(t.id))}}if(r)try{const e=r.getCLISessionClient()
|
|
1201
|
+
if(e){const t=[...I,...C]
|
|
1202
|
+
b=await e.batchEnrich(t)}}catch{}const _=g.replace(/\/$/,""),E=await Promise.allSettled(k.map((e=>fetch(`${_}/session/${e.id}/message`).then((e=>e.ok?e.json():[])).catch((()=>[]))))),q=[]
|
|
1203
|
+
for(let e=0;e<k.length;e++){const t=k[e],r=Date.now()-t.time.created
|
|
1204
|
+
let o=0,s=null,l=[],h=c(null,t.time.updated)
|
|
1205
|
+
const g=E[e],p="fulfilled"===g.status?g.value:[]
|
|
1264
1206
|
for(const e of p)"assistant"===e.info.role&&e.info.tokens&&(o+=(e.info.tokens.input||0)+(e.info.tokens.output||0)+(e.info.tokens.reasoning||0))
|
|
1265
|
-
if(p.length>0){const e=
|
|
1266
|
-
h=
|
|
1207
|
+
if(p.length>0){const e=i(p)
|
|
1208
|
+
h=c(e.lastActivityTime,t.time.updated),s=e.current||null,l=e.recent}const f=h.status
|
|
1267
1209
|
if(void 0!==u&&u>o)continue
|
|
1268
1210
|
if(void 0!==d&&o>d)continue
|
|
1269
|
-
const m=
|
|
1211
|
+
const m=b[t.id]
|
|
1270
1212
|
if(n.agentType&&(!m||m.agentType!==n.agentType))continue
|
|
1271
1213
|
if("archived"===m?.status)continue
|
|
1272
1214
|
let y=""
|
|
1273
|
-
const
|
|
1274
|
-
|
|
1275
|
-
|
|
1276
|
-
const
|
|
1277
|
-
|
|
1278
|
-
const
|
|
1279
|
-
|
|
1280
|
-
const
|
|
1281
|
-
|
|
1282
|
-
|
|
1215
|
+
const I=[],C=[]
|
|
1216
|
+
m?.associations&&C.push(...m.associations)
|
|
1217
|
+
const _=v[t.id]
|
|
1218
|
+
if(_)for(const e of _){const t=b[e]
|
|
1219
|
+
if(t?.associations){const r=w[e]?.type||"idle",n="idle"===r||"stalled"===r
|
|
1220
|
+
for(const e of t.associations)n&&!e.endedAt?C.push({...e,endedAt:"idle"}):C.push(e)}}if(C.length>0){const e=new Map
|
|
1221
|
+
for(const t of C){const r=e.get(t.requestLocalId)
|
|
1222
|
+
void 0!==r&&(r||t.endedAt)||e.set(t.requestLocalId,!t.endedAt)}const t=[...e.entries()].filter((([,e])=>e)).map((([e])=>e)),r=[...e.entries()].filter((([,e])=>!e)).map((([e])=>e))
|
|
1223
|
+
I.push(...t,...r)
|
|
1224
|
+
const n=[]
|
|
1225
|
+
if(t.length>0&&n.push("active: "+t.join(", ")),r.length>0){const e=5,t=r.slice(0,e),o=r.length-t.length
|
|
1226
|
+
n.push(`prev: ${t.join(", ")}${o>0?` +${o} more`:""}`)}n.length>0&&(y=` [${n.join(" | ")}]`)}if(a&&!I.includes(a))continue
|
|
1227
|
+
const S=t.title||"Untitled",T=S.length>50?S.slice(0,47)+"...":S
|
|
1228
|
+
q.push({id:t.id,title:T,status:f,age:r,totalTokens:o,requestsInfo:y,allRequestIds:I,statusDetail:h.detail,specialization:m?.specialization??null,currentAction:s,recentActions:l})}if(0===q.length)return{content:[{type:"text",text:"No sessions match the specified filters."}]}
|
|
1229
|
+
const S=l?q.slice(0,l):q,T=S.map((e=>{const t=e.specialization?"\n Specialization: "+e.specialization:"",r=e.currentAction?"\n Current: "+e.currentAction:"",o="specialist"!==n.agentType&&e.recentActions.length>0?"\n Recent: "+e.recentActions.join(", "):""
|
|
1230
|
+
return`\u2022 ${e.id}\n ${e.title}${t}\n Status: ${e.status} (${e.statusDetail}) | Age: ${s(e.age)} | ${e.totalTokens.toLocaleString()} tokens${e.requestsInfo}${r}${o}`})),R=l&&q.length>l?` (showing ${l} of ${q.length})`:""
|
|
1231
|
+
return{content:[{type:"text",text:`Found ${S.length} session${1!==S.length?"s":""}${R}:\n\n${T.join("\n\n")}`}]}}catch(e){throw Error("Failed to list sessions: "+(0,_.getErrorMessage)(e))}}var g,p=this&&this.__createBinding||(Object.create?function(e,t,r,n){void 0===n&&(n=r)
|
|
1283
1232
|
var o=Object.getOwnPropertyDescriptor(t,r)
|
|
1284
|
-
o&&!("get"in o?!t.__esModule:o.writable||o.configurable)||(o={enumerable:!0,get(){return t[r]}}),Object.defineProperty(e,n,o)}:function(e,t,r,n){void 0===n&&(n=r),e[n]=t[r]}),
|
|
1233
|
+
o&&!("get"in o?!t.__esModule:o.writable||o.configurable)||(o={enumerable:!0,get(){return t[r]}}),Object.defineProperty(e,n,o)}:function(e,t,r,n){void 0===n&&(n=r),e[n]=t[r]}),f=this&&this.__setModuleDefault||(Object.create?function(e,t){Object.defineProperty(e,"default",{enumerable:!0,value:t})}:function(e,t){e.default=t}),m=this&&this.__importStar||(g=function(e){return g=Object.getOwnPropertyNames||function(e){var t=[]
|
|
1285
1234
|
for(var r in e)({}).hasOwnProperty.call(e,r)&&(t[t.length]=r)
|
|
1286
|
-
return t},
|
|
1235
|
+
return t},g(e)},function(e){if(e&&e.__esModule)return e
|
|
1287
1236
|
var t={}
|
|
1288
|
-
if(null!=e)for(var r=
|
|
1289
|
-
return
|
|
1290
|
-
Object.defineProperty(exports,"__esModule",{value:!0}),exports.handleSpawn=
|
|
1237
|
+
if(null!=e)for(var r=g(e),n=0;n<r.length;n++)"default"!==r[n]&&p(t,e,r[n])
|
|
1238
|
+
return f(t,e),t})
|
|
1239
|
+
Object.defineProperty(exports,"__esModule",{value:!0}),exports.handleSpawn=n,exports.handleContinue=o,exports.handleCheckStatus=u,exports.handleAbort=d,exports.handleListSessions=h,exports.handleSubagentOperations=async function(e,t,r,s,i,a){const c=r.child({tool:"subagent_operations"}),l=s.startTimer("tool_execution_time")
|
|
1291
1240
|
try{if(e&&!e.operation&&(e.spawn?e.operation="spawn":e.continue?e.operation="continue":e.readMessages?e.operation="read-messages":e.listSessions?e.operation="list-sessions":e.prompt&&(e.agent||e.description)?e={operation:"spawn",spawn:{agent:e.agent||"coder",prompt:e.prompt,description:e.description||e.prompt.slice(0,60),requestId:e.requestId,allowParallel:e.allowParallel,useExistingSession:e.useExistingSession}}:e.sessionId&&e.prompt&&!e.spawn?e={operation:"continue",sessionId:e.sessionId,continue:{prompt:e.prompt}}:e.sessionId&&(e={operation:"check-status",sessionId:e.sessionId})),e?.spawn&&"string"==typeof e.spawn)try{e.spawn=JSON.parse(e.spawn)}catch{}if(e?.continue&&"string"==typeof e.continue)try{e.continue=JSON.parse(e.continue)}catch{}"spawn"===e?.operation&&e?.prompt&&!e?.spawn&&(e.spawn={agent:e.agent||"coder",prompt:e.prompt,description:e.description||e.prompt.slice(0,60),requestId:e.requestId},delete e.prompt,delete e.agent,delete e.description,delete e.requestId),"continue"===e?.operation&&e?.prompt&&!e?.continue&&(e.continue={prompt:e.prompt},delete e.prompt)
|
|
1292
|
-
const r=
|
|
1241
|
+
const r=C.validateArgs(e,v.SubagentOperationsSchema),{sessionId:g,operation:p}=r
|
|
1293
1242
|
let f
|
|
1294
|
-
switch(c.info("Processing subagent_operations",{operation:p,sessionId:
|
|
1243
|
+
switch(c.info("Processing subagent_operations",{operation:p,sessionId:g}),p){case"spawn":f=await n(r.spawn,t,c,i,a)
|
|
1295
1244
|
break
|
|
1296
|
-
case"continue":f=await
|
|
1245
|
+
case"continue":f=await o(g,r.continue.prompt,t,c,i,void 0,a)
|
|
1297
1246
|
break
|
|
1298
|
-
case"check-status":f=await
|
|
1247
|
+
case"check-status":f=await u(g,t,c,i)
|
|
1299
1248
|
break
|
|
1300
|
-
case"abort":f=await
|
|
1249
|
+
case"abort":f=await d(g,t,c)
|
|
1301
1250
|
break
|
|
1302
1251
|
case"read-messages":const e=r.readMessages?.limit??1
|
|
1303
|
-
f=await async function(e,t,r,n){const o=await(0,
|
|
1304
|
-
if(!o)throw new
|
|
1252
|
+
f=await async function(e,t,r,n){const o=await(0,k.getServerUrl)(r,n)
|
|
1253
|
+
if(!o)throw new y.ValidationError("Could not determine OpenCode server URL")
|
|
1305
1254
|
n.info("Reading messages from subagent session",{sessionId:e,limit:t})
|
|
1306
1255
|
try{const r=`${o.replace(/\/$/,"")}/session/${e}/message?limit=${t}`,n=await fetch(r)
|
|
1307
1256
|
if(!n.ok){if(404===n.status)return{content:[{type:"text",text:`Session ${e} not found.`}],isError:!0}
|
|
@@ -1309,13 +1258,13 @@ throw Error("Failed to fetch messages: "+n.status)}const s=await n.json()
|
|
|
1309
1258
|
if(0===s.length)return{content:[{type:"text",text:`Session ${e} has no messages yet.`}]}
|
|
1310
1259
|
const i=s.map(((e,t)=>{const r="user"===e.info.role?"USER":"ASSISTANT",n=e.parts.filter((e=>"text"===e.type&&e.text)).map((e=>e.text)).join("\n"),o=n.length>5e3?n.slice(0,5e3)+"...[truncated]":n
|
|
1311
1260
|
return`[${t+1}] ${r} (${new Date(e.info.time.created).toLocaleTimeString()}):\n${o}`})).join("\n\n---\n\n")
|
|
1312
|
-
return{content:[{type:"text",text:`Session ${e} - Last ${s.length} messages:\n\n${i}`}]}}catch(e){throw Error("Failed to read messages: "+(0,
|
|
1261
|
+
return{content:[{type:"text",text:`Session ${e} - Last ${s.length} messages:\n\n${i}`}]}}catch(e){throw Error("Failed to read messages: "+(0,_.getErrorMessage)(e))}}(g,e,t,c)
|
|
1313
1262
|
break
|
|
1314
|
-
case"list-sessions":const
|
|
1315
|
-
f=await
|
|
1263
|
+
case"list-sessions":const s={activeOnly:r.listSessions?.activeOnly,requestId:r.listSessions?.requestId,limit:r.listSessions?.limit,minTokens:r.listSessions?.minTokens,maxTokens:r.listSessions?.maxTokens,maxAgeHours:r.listSessions?.maxAgeHours,parentSessionId:a?.sessionId}
|
|
1264
|
+
f=await h(t,c,i,s)
|
|
1316
1265
|
break
|
|
1317
|
-
default:throw new
|
|
1318
|
-
const
|
|
1266
|
+
default:throw new y.ValidationError("Unknown operation: "+p)}return l({success:!0}),s.incrementCounter(`subagent_operations_${p}_success`,1),f}catch(e){return c.error("Subagent operations failed",{error:e instanceof Error?e.stack:e+""}),l({success:!1}),s.incrementCounter("subagent_operations_errors",1),{content:[{type:"text",text:"Subagent operation failed: "+(0,_.getErrorMessage)(e)}],isError:!0}}}
|
|
1267
|
+
const y=t(9860),w=t(8035),k=t(7617),b=t(6688),I=t(7280),v=t(6183),C=m(t(5967)),_=t(8824),E=t(9896),q=t(6928),S=t(8955),T=3456,R=6e4,P=3e5},1791(e,exports,t){"use strict"
|
|
1319
1268
|
function r(e,t){return t.info("Creating project context middleware",{projectId:e}),(t,r,n)=>{"GET"===t.method&&(t.query.projectId=e),["POST","PATCH","PUT"].includes(t.method)&&t.body&&(t.body.projectId=e),n()}}var n=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}}
|
|
1320
1269
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.ProjectContext=void 0,exports.projectContextMiddleware=r
|
|
1321
1270
|
const o=n(t(9896)),s=n(t(6928)),i=t(4139),a=t(4055),c=t(8824)
|
|
@@ -1517,12 +1466,11 @@ const r=t(1181),n=t(2960),o=t(8824)},2140(e,exports,t){"use strict"
|
|
|
1517
1466
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.handleSwitchToMainBranch=async function(e,t,i,a,c){const l=a.child({tool:"switch_to_main_branch"}),u=Date.now()
|
|
1518
1467
|
try{if(r.SwitchToMainBranchSchema.parse(e),l.info("Switching to main branch/repository"),!t.workspaceManager)throw(0,n.createServiceError)("WorkspaceManager not available",{phase:"workspace_manager_check"})
|
|
1519
1468
|
let a=null
|
|
1520
|
-
|
|
1469
|
+
l.info("Checking for requests to unlock")
|
|
1521
1470
|
try{const{sessionTag:e}=(0,o.getGlobalClientInfo)(),r=t.workspaceManager.getCurrentContext()
|
|
1522
1471
|
if(r.requestId&&"main"!==r.requestId){l.info("Unlocking current request before switching to main",{requestId:r.requestId,sessionTag:e})
|
|
1523
1472
|
try{const t=await i.unlockRequest(r.requestId,e)
|
|
1524
|
-
!1===t.locked?(a=r.requestId,l.info("Successfully unlocked request",{requestId:r.requestId,unlockedAt:t.unlockedAt})):l.warn("Request unlock returned unexpected result",{requestId:r.requestId,result:t})}catch(t){l.warn("Failed to unlock request (continuing with switch to main)",{requestId:r.requestId,sessionTag:e,error:t instanceof Error?t.message:t+""})}}else l.debug("No request context to unlock",{currentRequestId:r.requestId})}catch(e){l.warn("Error during request unlock check (continuing with switch)",{error:(0,s.getErrorMessage)(e)})}
|
|
1525
|
-
const d=await t.workspaceManager.switchToMain()
|
|
1473
|
+
!1===t.locked?(a=r.requestId,l.info("Successfully unlocked request",{requestId:r.requestId,unlockedAt:t.unlockedAt})):l.warn("Request unlock returned unexpected result",{requestId:r.requestId,result:t})}catch(t){l.warn("Failed to unlock request (continuing with switch to main)",{requestId:r.requestId,sessionTag:e,error:t instanceof Error?t.message:t+""})}}else l.debug("No request context to unlock",{currentRequestId:r.requestId})}catch(e){l.warn("Error during request unlock check (continuing with switch)",{error:(0,s.getErrorMessage)(e)})}const d=await t.workspaceManager.switchToMain()
|
|
1526
1474
|
if(!d.success)throw(0,n.createServiceError)("Failed to switch to main: "+d.message,{error:d.message})
|
|
1527
1475
|
const h=Date.now()-u
|
|
1528
1476
|
c.recordValue("switch_to_main_branch_time",h),c.incrementCounter("switch_to_main_branch_success",1)
|
|
@@ -1616,53 +1564,44 @@ for(const e of h){const{normalizedPath:r,fullPath:n}=u.validateAndNormalizePath(
|
|
|
1616
1564
|
_.push({source:r,destination:o,fullSource:n,fullDestination:s})}b=u.FileOperationPhase.TASK_VALIDATION,i.incrementCounter("move_files_phase",1,{phase:b})
|
|
1617
1565
|
const E=await u.validateTaskId(d,_[0].source,r,m,i,I.metricsPrefix),q=E?.requestId,S=await u.validateWorkItemStates(d,_[0].source,r,o,t,m,i,I.metricsPrefix),T=await u.autoPromoteTaskStatus(d,E.status,q,S.request?.status,_[0].source,r,o,m,i,I.metricsPrefix)
|
|
1618
1566
|
T.taskPromoted&&m.info(`Auto-promoted task ${d} (${E.title||"Untitled"}) to in_progress for file operations`,{taskId:d,taskTitle:E.title,previousStatus:E.status,newStatus:T.newTaskStatus,operationCount:h.length}),T.requestPromoted&&m.info(`Auto-promoted request ${q} to in_progress for file operations`,{requestId:q,previousStatus:S.request?.status,newStatus:T.newRequestStatus,triggeringTaskId:d})
|
|
1619
|
-
const
|
|
1620
|
-
if(!
|
|
1621
|
-
throw Error(
|
|
1567
|
+
const R=await u.ensureCorrectWorkspaceContext({taskPromoted:T.taskPromoted,requestId:q,context:t,operation:"move-files",logger:m,metrics:i,metricsPrefix:I.metricsPrefix})
|
|
1568
|
+
if(!R.success){if(R.isLockConflict)return{content:[{type:"text",text:"\u274c "+R.error}],isError:!0}
|
|
1569
|
+
throw Error(R.error)}let P={hadUserMods:!1,userModsCommitHash:void 0}
|
|
1622
1570
|
if(t.git)try{m.debug("[MOVE-FILES] Checking for user changes before move operations")
|
|
1623
1571
|
const e=await(0,g.commitUserChangesBeforeToolOperation)(t.git,"move-files",{requestId:q,taskId:d,workspaceManager:t.workspaceManager},m,i)
|
|
1624
|
-
e.userChangesCommitted&&(m.debug("[MOVE-FILES] User changes committed before move operations",{commitHash:e.commitHash?.substring(0,8),filesCommitted:e.filesCommitted}),m.info("User changes committed before move-files operation",{taskId:d,moveOperationsCount:_.length,userCommitHash:e.commitHash?.substring(0,8),userFilesCommitted:e.filesCommitted}),
|
|
1625
|
-
const{toolRecordId:
|
|
1626
|
-
w=
|
|
1627
|
-
const
|
|
1628
|
-
let
|
|
1572
|
+
e.userChangesCommitted&&(m.debug("[MOVE-FILES] User changes committed before move operations",{commitHash:e.commitHash?.substring(0,8),filesCommitted:e.filesCommitted}),m.info("User changes committed before move-files operation",{taskId:d,moveOperationsCount:_.length,userCommitHash:e.commitHash?.substring(0,8),userFilesCommitted:e.filesCommitted}),P={hadUserMods:!0,userModsCommitHash:e.commitHash})}catch(e){m.debug("[MOVE-FILES] Pre-tool commit failed, continuing with move operations",{error:e instanceof Error?e.message:e+""}),m.warn("Pre-tool user changes commit failed, continuing with move operation",{taskId:d,moveOperationsCount:_.length,error:e instanceof Error?e.message:e+""})}m.debug("[MOVE-FILES] Proceeding with move operations",{operationCount:_.length}),b=u.FileOperationPhase.RECORD_CREATION,i.incrementCounter("move_files_phase",1,{phase:b})
|
|
1573
|
+
const{toolRecordId:M,localToolRecordId:x}=await u.createFileOperationRecords(d,q,t.projectId,I.recordType,_[0].source,{operationCount:h.length,operations:_.map((e=>({source:e.source,destination:e.destination}))),userComment:v,hadUserMods:P.hadUserMods,userModsCommitHash:P.userModsCommitHash},r,n,m,i,I.metricsPrefix,f)
|
|
1574
|
+
w=M,k=M,b=I.fileOperationPhase,i.incrementCounter("move_files_phase",1,{phase:b})
|
|
1575
|
+
const j=[]
|
|
1576
|
+
let O=0
|
|
1629
1577
|
for(const e of _){const t={operation:{source:e.source,destination:e.destination},success:!1}
|
|
1630
1578
|
try{try{await a.default.access(e.fullSource)}catch(t){throw Error("Source path not accessible: "+e.source)}const r=(await a.default.stat(e.fullSource)).isDirectory()
|
|
1631
1579
|
t.isDirectory=r
|
|
1632
1580
|
const n=c.default.dirname(e.fullDestination)
|
|
1633
|
-
try{await a.default.mkdir(n,{recursive:!0})}catch(e){throw Error("Failed to create destination directory: "+n)}try{throw await a.default.access(e.fullDestination),Error("Destination already exists: "+e.destination)}catch(e){if(!(e instanceof Error&&e.message.includes("ENOENT")))throw e}await a.default.rename(e.fullSource,e.fullDestination),t.success=!0,
|
|
1634
|
-
i.recordValue("move_files_time",$),i.incrementCounter("move_files_operations_total",h.length),i.incrementCounter("move_files_operations_success",
|
|
1581
|
+
try{await a.default.mkdir(n,{recursive:!0})}catch(e){throw Error("Failed to create destination directory: "+n)}try{throw await a.default.access(e.fullDestination),Error("Destination already exists: "+e.destination)}catch(e){if(!(e instanceof Error&&e.message.includes("ENOENT")))throw e}await a.default.rename(e.fullSource,e.fullDestination),t.success=!0,O++,m.info("Successfully moved "+(r?"directory":"file"),{source:e.source,destination:e.destination,isDirectory:r})}catch(r){t.error=(0,p.getErrorMessage)(r),m.warn(`Failed to move ${e.source} to ${e.destination}`,{error:t.error})}j.push(t)}const $=Date.now()-y
|
|
1582
|
+
i.recordValue("move_files_time",$),i.incrementCounter("move_files_operations_total",h.length),i.incrementCounter("move_files_operations_success",O),i.incrementCounter("move_files_operations_failed",h.length-O),O===h.length?i.incrementCounter("move_files_success",1):O>0?i.incrementCounter("move_files_partial_success",1):i.incrementCounter("move_files_total_failure",1)
|
|
1635
1583
|
let D=null
|
|
1636
|
-
if(
|
|
1637
|
-
const e=
|
|
1638
|
-
D=await u.commitToGit(d,_[0].destination,
|
|
1639
|
-
const A=
|
|
1640
|
-
await u.updateFileOperationRecords(d,w,k,_[0].source,I.recordType,
|
|
1584
|
+
if(O>0){b=u.FileOperationPhase.GIT_COMMIT,i.incrementCounter("move_files_phase",1,{phase:b})
|
|
1585
|
+
const e=j.filter((e=>e.success)),r=1===e.length?`Move ${e[0].isDirectory?"directory":"file"} from ${e[0].operation.source} to ${e[0].operation.destination} - ${v}`:`Move ${e.length} ${1===e.length?"item":"items"} - ${v}`
|
|
1586
|
+
D=await u.commitToGit(d,_[0].destination,M,x,r,t,m,i,I.metricsPrefix)}b=u.FileOperationPhase.RECORD_UPDATE_SUCCESS,i.incrementCounter("move_files_phase",1,{phase:b})
|
|
1587
|
+
const A=j.filter((e=>e.success)),F=j.filter((e=>!e.success))
|
|
1588
|
+
await u.updateFileOperationRecords(d,w,k,_[0].source,I.recordType,O===h.length?`Successfully moved all ${h.length} items`:`Moved ${O}/${h.length} items successfully`,{status:O===h.length?"completed":"partial_success",commitHash:D?.commitHash,previousCommitHash:D?.previousCommitHash,operationCount:h.length,successCount:O,failureCount:h.length-O,successfulOperations:A.map((e=>({source:e.operation.source,destination:e.operation.destination,isDirectory:e.isDirectory}))),failedOperations:F.map((e=>({source:e.operation.source,destination:e.operation.destination,error:e.error}))),userComment:v,hadUserMods:P.hadUserMods,userModsCommitHash:P.userModsCommitHash},O===h.length?`Successfully moved all ${h.length} items`:`Moved ${O}/${h.length} items successfully`,r,n,m,i,I.metricsPrefix)
|
|
1641
1589
|
const N=t.getCurrentBranchContext?await t.getCurrentBranchContext():{branch:null,requestId:null,isMain:!0}
|
|
1642
1590
|
let L=""
|
|
1643
|
-
if(
|
|
1644
|
-
else if(
|
|
1645
|
-
L=`Successfully moved ${
|
|
1646
|
-
return D?.commitHash&&(L+="\nCommit: "+D.commitHash.substring(0,8)),N.requestId&&(L+="\nBranch: "+N.requestId),
|
|
1591
|
+
if(O===h.length)L=`Successfully moved all ${h.length} ${1===h.length?"item":"items"}`
|
|
1592
|
+
else if(O>0){const e=j.filter((e=>!e.success))
|
|
1593
|
+
L=`Successfully moved ${O}/${h.length} items.\n\nFailed operations:\n`+e.map((e=>`\u2022 ${e.operation.source} \u2192 ${e.operation.destination}: ${e.error}`)).join("\n")}else L="All move operations failed:\n"+j.map((e=>`\u2022 ${e.operation.source} \u2192 ${e.operation.destination}: ${e.error}`)).join("\n")
|
|
1594
|
+
return D?.commitHash&&(L+="\nCommit: "+D.commitHash.substring(0,8)),N.requestId&&(L+="\nBranch: "+N.requestId),R.lockAcquired&&R.lockedRequestId&&(L+="\n\u{1f512} **Locked request:** "+R.lockedRequestId),{content:[{type:"text",text:L}],isError:0===O}}catch(o){if(e.taskId&&n)try{const r=o instanceof d.NotFoundError||o instanceof d.ValidationError||o instanceof h.ZodError
|
|
1647
1595
|
await n.createToolRecord({...r?{}:{taskId:e.taskId},projectId:t.projectId,type:"move-files",metadata:{status:"failed",timestamp:(new Date).toISOString(),operationCount:e.operations?.length||0,operations:e.operations||[],userComment:e.comment,error:(0,p.getErrorMessage)(o),errorDetails:o instanceof Error?o.stack:o+"",phase:b,attemptedTaskId:e.taskId,taskIdValidationFailed:r},note:"Failed to move files - "+(0,p.getErrorMessage)(o)})}catch(t){m.error("Failed to create failure record for move-files operation",{error:t instanceof Error?t.message:t+"",taskId:e.taskId,operationCount:e.operations?.length||0})}const s=Date.now()-y
|
|
1648
1596
|
if(i.recordValue("move_files_time",s),i.incrementCounter("move_files_errors",1),m.error("Error in move-files operation:",{error:(0,p.getErrorMessage)(o),time:s}),(w||k)&&e.taskId){b=u.FileOperationPhase.RECORD_UPDATE_FAILURE
|
|
1649
1597
|
try{await u.updateFileOperationRecords(e.taskId,w,k,e.operations?.[0]?.source||"unknown",I.recordType,"Failed to move files",{status:"failed",error:(0,p.getErrorMessage)(o),operationCount:e.operations?.length||0,operations:e.operations||[],userComment:e.comment},"Failed to move files",r,n,m,i,I.metricsPrefix)}catch(t){m.error("Failed to update record with failure status",{taskId:e.taskId,recordId:w,error:t instanceof Error?t.message:t+""})}}return u.handleFileOperationError(o,b,m,i,e,I)}}
|
|
1650
1598
|
const a=i(t(1943)),c=i(t(6928)),l=t(6183),u=s(t(5967)),d=t(9860),h=t(1569),g=t(7478),p=t(8824)},2422(module){"use strict"
|
|
1651
|
-
module.exports=require("@modelcontextprotocol/sdk/server/sse.js")},
|
|
1652
|
-
Object.defineProperty(exports,"__esModule",{value:!0}),exports.ensureRequestWorktree=async function(e,t,i){const a="requests/"+t,c=(0,n.join)(e,s.ALCHEMY_DIR_NAME,"worktrees"),l=(0,n.join)(c,t)
|
|
1653
|
-
if((0,r.existsSync)(l))return void i.info("Worktree already exists on disk, skipping pre-spawn creation",{requestId:t,worktreePath:l})
|
|
1654
|
-
const u=(0,o.simpleGit)(e);(0,r.mkdirSync)(c,{recursive:!0})
|
|
1655
|
-
try{await u.raw(["worktree","prune"])}catch{}const d=await u.branch(),h=d.all.includes(a)
|
|
1656
|
-
try{if(h)await u.raw(["worktree","add",l,a]),i.info("Pre-spawn: created worktree for existing branch",{requestId:t,branchName:a,worktreePath:l})
|
|
1657
|
-
else{const e=d.all.includes("main")?"main":"master"
|
|
1658
|
-
await u.raw(["worktree","add","-b",a,l,e]),i.info("Pre-spawn: created worktree with new branch from latest main",{requestId:t,branchName:a,mainBranch:e,worktreePath:l})}}catch(e){const r=e instanceof Error?e.message:e+""
|
|
1659
|
-
i.warn("Pre-spawn: failed to create worktree (MCP process will retry)",{requestId:t,error:r})}}
|
|
1660
|
-
const r=t(9896),n=t(6928),o=t(3807),s=t(4139)},2425(e,exports,t){"use strict"
|
|
1599
|
+
module.exports=require("@modelcontextprotocol/sdk/server/sse.js")},2425(e,exports,t){"use strict"
|
|
1661
1600
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.def=void 0
|
|
1662
1601
|
const r=t(6183),n=t(3707)
|
|
1663
1602
|
exports.def={name:"quick_manage",description:"Move, delete, or create directories. Wraps the change in a request/task workflow that auto-completes.\n\nProvide an array of operations, each with operationType and corresponding data:\n\u2022 create-directory: { createDirectory: { path } }\n\u2022 move-files: { moveFiles: { moves: [{ source, destination }] } }\n\u2022 delete-files: { deleteFiles: { targets: [{ path }] } }\n\nFor read-only operations like get-file-info, use manage_files instead.\n\nRequires: title, description, operations.",schema:r.QuickManageSchema,annotations:{title:"Quick Manage",readOnlyHint:!1,destructiveHint:!0,idempotentHint:!1},handler(e,t){return(0,n.handleQuickChange)(e,"manage",t.context,t.apiClient,t.logger,t.metrics,t.mcpServer)}}},2462(e,exports,t){"use strict"
|
|
1664
1603
|
Object.defineProperty(exports,"__esModule",{value:!0})
|
|
1665
|
-
const r=t(2245),n=t(9080),o=t(5692),s=t(9030),i=t(2903),a=t(4607),c=t(9499),l=t(6770),u=t(8045),d=t(9697),h=t(9196),g=t(5459),p=t(4805),f=t(260),m=t(2283),y=t(4165),w=t(7834),k=t(9373),b=t(6111),I=t(700),v=t(2783),C=t(2601),_=t(1722),E=t(7257),q=t(9230),S=t(5216),T=t(6473),
|
|
1604
|
+
const r=t(2245),n=t(9080),o=t(5692),s=t(9030),i=t(2903),a=t(4607),c=t(9499),l=t(6770),u=t(8045),d=t(9697),h=t(9196),g=t(5459),p=t(4805),f=t(260),m=t(2283),y=t(4165),w=t(7834),k=t(9373),b=t(6111),I=t(700),v=t(2783),C=t(2601),_=t(1722),E=t(7257),q=t(9230),S=t(5216),T=t(6473),R=t(4921),P=t(8850),M=t(3556),x=t(1391),j=t(6315),O=t(7713),$=t(6252),D=t(213),A=t(7250),F=t(2425),N=t(1540),L=t(5767),z=t(4973),B=t(509),H=t(7613),U=t(3322),G=t(5247),W=t(542);(0,r.registerTool)(n.def),(0,r.registerTool)(o.def),(0,r.registerTool)(s.def),(0,r.registerTool)(i.def),(0,r.registerTool)(a.def),(0,r.registerTool)(c.def),(0,r.registerTool)(l.def),(0,r.registerTool)(u.def),(0,r.registerTool)(d.def),(0,r.registerTool)(h.def),(0,r.registerTool)(g.def),(0,r.registerTool)(p.def),(0,r.registerTool)(f.def),(0,r.registerTool)(m.def),(0,r.registerTool)(y.def),(0,r.registerTool)(w.def),(0,r.registerTool)(k.def),(0,r.registerTool)(b.def),(0,r.registerTool)(I.def),(0,r.registerTool)(v.def),(0,r.registerTool)(C.def),(0,r.registerTool)(_.def),(0,r.registerTool)(E.def),(0,r.registerTool)(q.def),(0,r.registerTool)(S.def),(0,r.registerTool)(T.def),(0,r.registerTool)(R.def),(0,r.registerTool)(P.def),(0,r.registerTool)(M.def),(0,r.registerTool)(x.def),(0,r.registerTool)(j.def),(0,r.registerTool)(O.def),(0,r.registerTool)($.def),(0,r.registerTool)(D.def),(0,r.registerTool)(A.def),(0,r.registerTool)(F.def),(0,r.registerTool)(N.def),(0,r.registerTool)(L.def),(0,r.registerTool)(z.def),(0,r.registerTool)(B.def),(0,r.registerTool)(H.def),(0,r.registerTools)(U.metaDefs),(0,r.registerTools)(G.testingDefs),(0,r.registerTools)(W.debugDefs),(0,t(2245).freezeRegistry)()},2478(e,exports){"use strict"
|
|
1666
1605
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.requestConfig=void 0,exports.areTestsRequiredForCompletion=function(){return exports.requestConfig.requireTestsForCompletion},exports.setTestsRequiredForCompletion=function(e){exports.requestConfig.requireTestsForCompletion=e},exports.getCompletionMode=function(e){return e&&["auto-merge","auto-test-then-merge","manual-review"].includes(e)?e:"auto-merge"},exports.getApprovalMode=function(e){return e&&["none","require-approval"].includes(e)?e:"none"},exports.requestConfig={requireTestsForCompletion:!1}},2537(e,exports,t){"use strict"
|
|
1667
1606
|
async function r(e,t,r){if(C.has(r)&&_>=t){if(0===t)return 0
|
|
1668
1607
|
try{return(await y.default.readFile(e,"utf-8")).split("\n").length}catch{return}}}function n(e,t,r){const n="depth"in e,o=n?e:r,s=n?e.isDirectory:e.isDirectory(),a=e.name,c=s?"[\u{1f4c1} DIR]":"[\u{1f4c4} FILE]"
|
|
@@ -1952,17 +1891,15 @@ return r.debug("Retrieved request ID from task",{taskId:e,requestId:s.requestId}
|
|
|
1952
1891
|
return r.warn("Failed to get request ID from task",{taskId:e,error:i}),n.incrementCounter("get_request_id_from_task_failure",1),o({success:!1,error:t instanceof Error?t.name:"unknown"}),null}},exports.validateTaskId=async function(e,t,r,n,i,a){try{const o=await r.getTask(e)
|
|
1953
1892
|
return n.info(`Task ID ${e} validated successfully`,{taskId:e,requestId:o.requestId,path:t}),i.incrementCounter(a+"_valid_task_id",1),o}catch(r){const c=(0,s.getErrorMessage)(r)
|
|
1954
1893
|
if(c.includes("404")||c.toLowerCase().includes("not found")||c.toLowerCase().includes("task not found"))throw n.error(`Task ID ${e} does not exist (404 Not Found)`,{taskId:e,path:t,error:c}),i.incrementCounter(a+"_task_not_found",1),new o.NotFoundError(`Task ${e} not found in project. Please provide a valid task ID.`,{taskId:e,path:t,originalError:r})
|
|
1955
|
-
throw n.error("Could not validate task ID "+e,{taskId:e,path:t,error:c}),i.incrementCounter(a+"_task_validation_error",1),new o.ValidationError(`Could not validate task ${e}: ${c}`,{taskId:e,path:t,originalError:r})}},exports.createReopenGuidanceMessage=r,exports.validateWorkItemStates=async function(e,t,n,a,c,l,u
|
|
1956
|
-
if(
|
|
1957
|
-
throw
|
|
1958
|
-
if(
|
|
1959
|
-
throw
|
|
1894
|
+
throw n.error("Could not validate task ID "+e,{taskId:e,path:t,error:c}),i.incrementCounter(a+"_task_validation_error",1),new o.ValidationError(`Could not validate task ${e}: ${c}`,{taskId:e,path:t,originalError:r})}},exports.createReopenGuidanceMessage=r,exports.validateWorkItemStates=async function(e,t,n,i,a,c,l,u){try{const a=await n.getTask(e)
|
|
1895
|
+
if(c.info("Validating work item states for task "+e,{taskId:e,taskStatus:a.status,requestId:a.requestId,path:t}),c.info("STRICT VALIDATION - Task details",{taskId:e,taskStatus:a.status,requestId:a.requestId,taskTitle:a.title,path:t,timestamp:(new Date).toISOString()}),"completed"===a.status||"canceled"===a.status||"reverted"===a.status){const n=r(e,a.requestId,a.status)
|
|
1896
|
+
throw c.error(`STRICT VALIDATION - File operation blocked on ${a.status} task`,{taskId:e,taskStatus:a.status,path:t,errorMessage:n}),l.incrementCounter(`${u}_blocked_${a.status}_task`,1),new o.ValidationError(n,{taskId:e,taskStatus:a.status,path:t,reason:"task_"+a.status})}let d,h
|
|
1897
|
+
if(a.requestId)try{if(d=await i.getRequest(a.requestId),c.info("Validating request status for "+a.requestId,{requestId:a.requestId,requestStatus:d.status,taskId:e,path:t}),c.info("STRICT VALIDATION - Request details",{requestId:a.requestId,requestStatus:d.status,requestTitle:d.title,taskId:e,path:t,timestamp:(new Date).toISOString()}),"pending_approval"===d.status||"ready_for_review"===d.status||"completed"===d.status||"canceled"===d.status){const n=r(e,a.requestId,a.status,d.status)
|
|
1898
|
+
throw c.error(`STRICT VALIDATION - File operation blocked on ${d.status} request`,{taskId:e,requestId:a.requestId,requestStatus:d.status,path:t,errorMessage:n}),l.incrementCounter(`${u}_blocked_${d.status}_request`,1),new o.ValidationError(n,{taskId:e,requestId:a.requestId,requestStatus:d.status,path:t,reason:"request_"+d.status})}}catch(r){if(r instanceof o.ValidationError)throw r
|
|
1960
1899
|
const n=(0,s.getErrorMessage)(r)
|
|
1961
|
-
|
|
1962
|
-
if("multi-agent"===r?.getCurrentContext().mode)l.debug("Skipping branch switching in multi-agent mode - worktrees handle branch isolation",{taskId:e,requestId:h.requestId,mode:"multi-agent",reason:"worktree_isolation"}),p={switched:!1,message:"Branch switching skipped in multi-agent mode (using worktrees)"}
|
|
1963
|
-
else try{p=await(0,i.ensureCorrectBranch)(h.requestId,e,t,c,l,u,d),p.switched&&l.info("Automatically switched to feature branch for file operation",{taskId:e,requestId:h.requestId,branchName:p.branchName,filePath:t})}catch(r){l.warn("Error during automatic branch switching",{taskId:e,requestId:h.requestId,filePath:t,error:(0,s.getErrorMessage)(r)}),p={switched:!1,message:"Branch switching error: "+(0,s.getErrorMessage)(r)}}}return u.incrementCounter(d+"_state_validation_success",1),{task:h,request:g,branchSwitch:p}}catch(r){if(r instanceof o.ValidationError)throw r
|
|
1900
|
+
c.warn("Could not validate request status for "+a.requestId,{taskId:e,requestId:a.requestId,error:n,path:t}),l.incrementCounter(u+"_request_validation_warning",1)}return c.info("Work item state validation passed",{taskId:e,taskStatus:a.status,requestId:a.requestId,requestStatus:d?.status,path:t}),a.requestId&&(c.debug("Worktrees handle branch isolation, skipping branch switching",{taskId:e,requestId:a.requestId}),h={switched:!1,message:"Branch switching skipped (using worktrees)"}),l.incrementCounter(u+"_state_validation_success",1),{task:a,request:d,branchSwitch:h}}catch(r){if(r instanceof o.ValidationError)throw r
|
|
1964
1901
|
const n=(0,s.getErrorMessage)(r)
|
|
1965
|
-
throw
|
|
1902
|
+
throw c.error("Could not validate work item states for task "+e,{taskId:e,path:t,error:n}),l.incrementCounter(u+"_state_validation_error",1),new o.ValidationError("Could not validate work item states: "+n,{taskId:e,path:t,originalError:r})}},exports.autoPromoteTaskStatus=async function(e,t,r,o,i,a,c,l,u,d){try{let s,h,g=!1,p=!1
|
|
1966
1903
|
if("pending"===t&&(l.info(`Auto-promoting task ${e} from pending to in_progress`,{taskId:e,currentStatus:t,path:i}),await a.updateTaskStatus(e,"in_progress"),l.info(`Successfully auto-promoted task ${e} to in_progress`,{taskId:e,previousStatus:t,newStatus:"in_progress",path:i}),u.incrementCounter(d+"_auto_promotion_success",1),g=!0,s="in_progress",r&&o)){const t=await n(r,o,e,"in_progress",c,l,u,d)
|
|
1967
1904
|
p=t.promoted,h=t.newStatus}return{taskPromoted:g,newTaskStatus:s,requestPromoted:p,newRequestStatus:h}}catch(r){const n=(0,s.getErrorMessage)(r)
|
|
1968
1905
|
return l.warn(`Failed to auto-promote task ${e} from pending to in_progress`,{taskId:e,currentStatus:t,error:n,path:i}),u.incrementCounter(d+"_auto_promotion_failure",1),{taskPromoted:!1,requestPromoted:!1}}},exports.autoPromoteRequestStatus=n,exports.validateRequestCompletionEligibility=async function(e,t,r,n,i){try{const s=await t.listTasks({requestId:e})
|
|
@@ -1983,7 +1920,7 @@ const s=`Cannot mark request as ready/complete. ${t.join(", ")}. Task breakdown:
|
|
|
1983
1920
|
throw r.warn("Request completion blocked due to unresolved tasks",{requestId:e,errorMessage:s,taskBreakdown:a}),n.incrementCounter(i+"_request_completion_blocked",1),new o.ValidationError(s,{requestId:e,taskBreakdown:a,unresolvedTasks:c,reason:"unresolved_tasks"})}return n.incrementCounter(i+"_request_completion_eligible",1),{eligible:!0,taskBreakdown:a}}catch(t){if(t instanceof o.ValidationError)throw t
|
|
1984
1921
|
const a=(0,s.getErrorMessage)(t)
|
|
1985
1922
|
throw r.error("Could not validate request completion eligibility for "+e,{requestId:e,error:a}),n.incrementCounter(i+"_request_completion_validation_error",1),new o.ValidationError("Could not validate request completion: "+a,{requestId:e,originalError:t})}}
|
|
1986
|
-
const o=t(9860),s=t(8824)
|
|
1923
|
+
const o=t(9860),s=t(8824)},2982(e,exports,t){"use strict"
|
|
1987
1924
|
function r(e){const t=[]
|
|
1988
1925
|
return"write-file"===e.type&&e.metadata?.path?t.push(e.metadata.path):"replace-in-files"===e.type&&e.metadata?.operations?e.metadata.operations.forEach((e=>{e.path&&t.push(e.path)})):"move-files"===e.type&&e.metadata?.successfulOperations?e.metadata.successfulOperations.forEach((e=>{e.destination&&t.push(e.destination)})):"delete-files"===e.type&&e.metadata?.paths?t.push(...e.metadata.paths):"manage-files"===e.type&&e.metadata?.operations&&e.metadata.operations.forEach((e=>{e.createDirectory?.path&&t.push(e.createDirectory.path),e.moveFiles?.moves&&e.moveFiles.moves.forEach((e=>{e.destination&&t.push(e.destination)})),e.deleteFiles?.targets&&e.deleteFiles.targets.forEach((e=>{e.path&&t.push(e.path)}))})),[...new Set(t)]}Object.defineProperty(exports,"__esModule",{value:!0}),exports.handleGenerateRequestJournal=async function(e,t,o,c,l){const u=c.child({tool:"generate_request_journal"}),d=l.startTimer("tool_execution_time")
|
|
1989
1926
|
try{const i=a.parse(e),{requestId:c}=i
|
|
@@ -2007,7 +1944,7 @@ if(u.info("Switching to request: "+h),!t.workspaceManager)throw(0,o.createServic
|
|
|
2007
1944
|
let g
|
|
2008
1945
|
try{if(g=await a.getRequest(h),!g)return{content:[{type:"text",text:`\u274c Request not found: Request ${h} does not exist. Please verify the request ID is correct.`}],isError:!0}}catch(e){if(e instanceof o.NotFoundError)return{content:[{type:"text",text:`\u274c Request not found: Request ${h} does not exist. Please verify the request ID is correct.`}],isError:!0}
|
|
2009
1946
|
throw(0,o.createServiceError)(`Failed to validate request ${h}: ${(0,i.getErrorMessage)(e)}`,{requestId:h,phase:"request_validation"})}if("reverted"===g.status)return{content:[{type:"text",text:`\u274c Branch for request ${h} does not exist - branch was deleted during revert process. Reverted requests cannot be switched to.`}],isError:!0}
|
|
2010
|
-
|
|
1947
|
+
"completed"===g.status&&u.info(`Attempting to switch to completed request ${h} - branch should be preserved`),"canceled"===g.status&&u.warn(`Attempting to switch to canceled request ${h} - branch may not exist`),u.info("Checking request lock",{requestId:h})
|
|
2011
1948
|
try{const{sessionTag:e}=(0,s.getGlobalClientInfo)(),n=await a.getRequestLockStatus(h)
|
|
2012
1949
|
if(n.isLocked&&n.lockedBySessionTag!==e){if(!n.isExpired){let e=`\u274c Request ${h} is currently locked by another agent (${n.lockedBySessionTag}).`
|
|
2013
1950
|
return e+="\n\nLock expires in: "+n.timeRemainingFormatted,e=await r(e,h,t,u),{content:[{type:"text",text:e}],isError:!0}}u.info("Attempting to clean up expired lock",{requestId:h,lockedBySessionTag:n.lockedBySessionTag,expiredLock:!0})
|
|
@@ -2024,24 +1961,21 @@ try{const t=await a.lockRequest(h,e)
|
|
|
2024
1961
|
if(!t.locked)return{content:[{type:"text",text:`\u274c Failed to acquire lock for request ${h}. Another agent may have locked it simultaneously.`}],isError:!0}
|
|
2025
1962
|
u.info("Successfully acquired request lock",{requestId:h,sessionTag:e,lockedAt:t.lockedAt})}catch(t){u.error("Failed to acquire request lock",{requestId:h,sessionTag:e,error:t instanceof Error?t.message:t+""})
|
|
2026
1963
|
const r=t instanceof Error?t.message:t+""
|
|
2027
|
-
return r.includes("already locked")?{content:[{type:"text",text:`\u274c Request ${h} is already locked by another agent. ${r}`}],isError:!0}:{content:[{type:"text",text:`\u274c Failed to acquire lock for request ${h}: ${r}`}],isError:!0}}}}catch(e){return u.error("Error checking/acquiring request lock",{requestId:h,error:(0,i.getErrorMessage)(e)}),{content:[{type:"text",text:"\u274c Failed to check request lock status: "+(0,i.getErrorMessage)(e)}],isError:!0}}
|
|
2028
|
-
u.info("Using unified workspace switching",{requestId:h})
|
|
1964
|
+
return r.includes("already locked")?{content:[{type:"text",text:`\u274c Request ${h} is already locked by another agent. ${r}`}],isError:!0}:{content:[{type:"text",text:`\u274c Failed to acquire lock for request ${h}: ${r}`}],isError:!0}}}}catch(e){return u.error("Error checking/acquiring request lock",{requestId:h,error:(0,i.getErrorMessage)(e)}),{content:[{type:"text",text:"\u274c Failed to check request lock status: "+(0,i.getErrorMessage)(e)}],isError:!0}}u.info("Using unified workspace switching",{requestId:h})
|
|
2029
1965
|
const p=await t.workspaceManager.switchToRequest(h,{isCompleted:"completed"===g.status})
|
|
2030
|
-
if(!p.success){
|
|
1966
|
+
if(!p.success){try{const{sessionTag:e}=(0,s.getGlobalClientInfo)()
|
|
2031
1967
|
u.warn("Workspace switch failed, attempting to release acquired lock",{requestId:h,sessionTag:e,switchError:p.message}),await a.unlockRequest(h,e),u.info("Successfully released lock after workspace switch failure",{requestId:h})}catch(e){u.error("Failed to release lock after workspace switch failure",{requestId:h,unlockError:e instanceof Error?e.message:e+""})}const e=p.message||"Unknown error"
|
|
2032
1968
|
if(e.includes("does not exist")||e.includes("Branch for request"))return{content:[{type:"text",text:`\u274c Branch for request ${h} does not exist. This can happen if:\n- Request was reverted (branch deleted during revert)\n- Request was completed and branch was cleaned up\n- Branch was manually deleted\n\nUse 'get-request-information' to check the request status.`}],isError:!0}
|
|
2033
1969
|
throw(0,o.createServiceError)(`Failed to switch to request ${h}: ${e}`,{requestId:h,error:e})}const f=Date.now()-d
|
|
2034
1970
|
l.recordValue("switch_to_request_branch_time",f),l.incrementCounter("switch_to_request_branch_success",1)
|
|
2035
1971
|
const m=["Successfully switched to branch: "+(p.newContext?.branchName||"unknown"),"**Previous branch:** "+(p.previousContext?.branchName||"unknown")]
|
|
2036
|
-
return
|
|
1972
|
+
return m.push("\u{1f512} **Locked request:** "+h),u.info("Successfully switched to request workspace",{requestId:h,mode:p.newContext?.mode,branch:p.newContext?.branchName,duration:f}),{content:[{type:"text",text:m.join("\n")}]}}catch(t){const r=Date.now()-d
|
|
2037
1973
|
if(l.recordValue("switch_to_request_branch_time",r),l.incrementCounter("switch_to_request_branch_error",1),u.error("Failed to switch to request branch",{requestId:e.requestId,error:(0,i.getErrorMessage)(t),duration:r}),t instanceof o.ValidationError||t instanceof o.NotFoundError)return{content:[{type:"text",text:"\u274c "+t.message}],isError:!0}
|
|
2038
1974
|
throw t}}
|
|
2039
1975
|
const n=t(6183),o=t(9860),s=t(5172),i=t(8824)},3217(e,exports,t){"use strict"
|
|
2040
|
-
Object.defineProperty(exports,"__esModule",{value:!0}),exports.MultiAgentWorkspaceManager=
|
|
2041
|
-
const r=t(
|
|
2042
|
-
Object.defineProperty(exports,"
|
|
2043
|
-
const n=t(7636)
|
|
2044
|
-
Object.defineProperty(exports,"MultiAgentWorkspaceManager",{enumerable:!0,get(){return n.MultiAgentWorkspaceManager}})},3253(e,exports){"use strict"
|
|
1976
|
+
Object.defineProperty(exports,"__esModule",{value:!0}),exports.MultiAgentWorkspaceManager=void 0,exports.createWorkspaceManager=function(e,t,n,o,s){return new r.MultiAgentWorkspaceManager(e,t,n,o,s)}
|
|
1977
|
+
const r=t(7636)
|
|
1978
|
+
Object.defineProperty(exports,"MultiAgentWorkspaceManager",{enumerable:!0,get(){return r.MultiAgentWorkspaceManager}})},3253(e,exports){"use strict"
|
|
2045
1979
|
function t(e){if(0>=e)return"Lock expired"
|
|
2046
1980
|
const t=Math.floor(e/1e3),r=Math.floor(t/60),n=Math.floor(r/60)
|
|
2047
1981
|
if(n>0){const e=r%60
|
|
@@ -2116,24 +2050,24 @@ const q=_.filter((e=>e.path)),S=_.filter((e=>e.documentId))
|
|
|
2116
2050
|
y.info("Operation breakdown",{fileOperations:q.length,documentOperations:S.length})
|
|
2117
2051
|
const T=[]
|
|
2118
2052
|
for(const e of q){const{normalizedPath:r,fullPath:n}=d.validateAndNormalizePath(e.path,t)
|
|
2119
|
-
T.push({type:"file",path:r,fullPath:n,replacements:e.replacements,mode:e.mode||"unique"})}const
|
|
2053
|
+
T.push({type:"file",path:r,fullPath:n,replacements:e.replacements,mode:e.mode||"unique"})}const R=[]
|
|
2120
2054
|
if(S.length>0&&!t.documentFileManager)throw Error("Document file manager not available - cannot process document operations")
|
|
2121
|
-
for(const e of S)
|
|
2122
|
-
if(
|
|
2055
|
+
for(const e of S)R.push({type:"document",documentId:e.documentId,replacements:e.replacements,mode:e.mode||"unique"})
|
|
2056
|
+
if(R.length>0&&t.apiClient){const e=R.map((e=>e.documentId))
|
|
2123
2057
|
try{await(0,f.ensureDocumentsNotLocked)(e,t.apiClient,y,a,"replace-strings-documents")}catch(e){if(e instanceof h.ValidationError)return{content:[{type:"text",text:e.message}],isError:!0}
|
|
2124
2058
|
throw e}}I=d.FileOperationPhase.TASK_VALIDATION,a.incrementCounter("replace_strings_phase",1,{phase:I})
|
|
2125
|
-
const
|
|
2126
|
-
let
|
|
2127
|
-
T.length>0&&x&&(
|
|
2128
|
-
let
|
|
2129
|
-
T.length>0&&x&&
|
|
2130
|
-
const $=await d.ensureCorrectWorkspaceContext({taskPromoted:
|
|
2059
|
+
const P=T.length>0?T[0].path:"document-operation",M=await d.validateTaskId(C,P,r,y,a,v.metricsPrefix),x=M?.requestId
|
|
2060
|
+
let j=null
|
|
2061
|
+
T.length>0&&x&&(j=await d.validateWorkItemStates(C,T[0].path,r,s,t,y,a,v.metricsPrefix))
|
|
2062
|
+
let O={taskPromoted:!1,requestPromoted:!1}
|
|
2063
|
+
T.length>0&&x&&j&&(O=await d.autoPromoteTaskStatus(C,M.status,x,j.request?.status,T[0].path,r,s,y,a,v.metricsPrefix),O.taskPromoted&&y.info("Auto-promoted task to in_progress for replace-strings operation",{taskId:C,requestId:x,previousStatus:M.status,newStatus:O.newTaskStatus,triggeringOperation:"replace-strings"}))
|
|
2064
|
+
const $=await d.ensureCorrectWorkspaceContext({taskPromoted:O.taskPromoted,requestId:x,context:t,operation:"replace-strings",logger:y,metrics:a,metricsPrefix:v.metricsPrefix})
|
|
2131
2065
|
if(!$.success){if($.isLockConflict)return{content:[{type:"text",text:"\u274c "+$.error}],isError:!0}
|
|
2132
2066
|
throw Error($.error)}if(T.length>0){y.debug("Re-validating file paths with correct workspace context",{operationCount:T.length,workspaceBasePath:t.workspaceManager?.getCurrentContext().basePath})
|
|
2133
2067
|
for(let e=0;e<T.length;e++){const r=T[e],n=q[e],{normalizedPath:o,fullPath:s}=d.validateAndNormalizePath(n.path,t)
|
|
2134
|
-
T[e]={...r,path:o,fullPath:s}}}if(
|
|
2068
|
+
T[e]={...r,path:o,fullPath:s}}}if(R.length>0&&x)try{await(0,g.validateRequestStatusForDocumentOperation)(x,s,y,a,"replace-strings-document")}catch(e){if(e instanceof h.ValidationError)return{content:[{type:"text",text:e.message}],isError:!0}
|
|
2135
2069
|
throw e}I=d.FileOperationPhase.RECORD_CREATION,a.incrementCounter("replace_strings_phase",1,{phase:I})
|
|
2136
|
-
const D=[...T.map((e=>({type:"file",path:e.path,replacements:e.replacements,mode:e.mode}))),...
|
|
2070
|
+
const D=[...T.map((e=>({type:"file",path:e.path,replacements:e.replacements,mode:e.mode}))),...R.map((e=>({type:"document",documentId:e.documentId,replacements:e.replacements,mode:e.mode})))],{toolRecordId:A}=await d.createFileOperationRecords(C,x,t.projectId,v.recordType,P,{operationCount:_.length,fileOperations:T.length,documentOperations:R.length,operations:D,userComment:E},r,o,y,a,v.metricsPrefix,c)
|
|
2137
2071
|
if(k=A,b=A,I=v.fileOperationPhase,a.incrementCounter("replace_strings_phase",1,{phase:I}),T.length>0&&t.git)try{y.debug("[REPLACE-STRINGS] Checking for user changes before replace operations")
|
|
2138
2072
|
const e=await(0,p.commitUserChangesBeforeToolOperation)(t.git,"replace-strings",{requestId:x,taskId:C,workspaceManager:t.workspaceManager},y,a)
|
|
2139
2073
|
e.userChangesCommitted&&(y.debug("[REPLACE-STRINGS] User changes committed before replace operations",{commitHash:e.commitHash?.substring(0,8),filesCommitted:e.filesCommitted}),y.info("User changes committed before replace-strings operation",{taskId:C,fileOperationsCount:T.length,userCommitHash:e.commitHash?.substring(0,8),userFilesCommitted:e.filesCommitted}))}catch(e){y.debug("[REPLACE-STRINGS] Pre-tool commit failed, continuing with replacements",{error:e instanceof Error?e.message:e+""}),y.warn("Pre-tool user changes commit failed, continuing with replace operation",{taskId:C,fileOperationsCount:T.length,error:e instanceof Error?e.message:e+""})}y.debug("[REPLACE-STRINGS] Proceeding with file operations",{fileCount:T.length})
|
|
@@ -2142,21 +2076,21 @@ let N=0,L=0
|
|
|
2142
2076
|
for(const e of T){const t={type:"file",path:e.path,success:!1,replacements:[],successfulReplacements:0,failedReplacements:0}
|
|
2143
2077
|
try{if(await l.default.access(e.fullPath),!(await l.default.stat(e.fullPath)).isFile())throw Error("Path is not a file: "+e.path)
|
|
2144
2078
|
const r=await l.default.readFile(e.fullPath,"utf8"),{newContent:o,results:s}=await n(r,e.replacements,e.mode)
|
|
2145
|
-
t.replacements=s,t.successfulReplacements=s.filter((e=>e.success)).length,t.failedReplacements=s.filter((e=>!e.success)).length,o!==r?(await l.default.writeFile(e.fullPath,o,"utf8"),t.success=!0,L++,y.info("File updated successfully",{path:e.path,successfulReplacements:t.successfulReplacements,failedReplacements:t.failedReplacements})):0===t.failedReplacements&&(t.success=!0),N+=t.failedReplacements}catch(r){t.error=(0,m.getErrorMessage)(r),t.failedReplacements=e.replacements.length,N+=t.failedReplacements,y.error("File operation failed",{path:e.path,error:t.error})}F.push(t)}for(const e of
|
|
2079
|
+
t.replacements=s,t.successfulReplacements=s.filter((e=>e.success)).length,t.failedReplacements=s.filter((e=>!e.success)).length,o!==r?(await l.default.writeFile(e.fullPath,o,"utf8"),t.success=!0,L++,y.info("File updated successfully",{path:e.path,successfulReplacements:t.successfulReplacements,failedReplacements:t.failedReplacements})):0===t.failedReplacements&&(t.success=!0),N+=t.failedReplacements}catch(r){t.error=(0,m.getErrorMessage)(r),t.failedReplacements=e.replacements.length,N+=t.failedReplacements,y.error("File operation failed",{path:e.path,error:t.error})}F.push(t)}for(const e of R){const r={type:"document",documentId:e.documentId,success:!1,replacements:[],successfulReplacements:0,failedReplacements:0}
|
|
2146
2080
|
try{const o=await t.documentFileManager.getDocumentAsFile(e.documentId),s=t.documentFileManager.getCachedDocumentInfo(e.documentId)
|
|
2147
2081
|
r.filename=s?.filename
|
|
2148
2082
|
const i=await l.default.readFile(o,"utf8"),{newContent:a,results:c}=await n(i,e.replacements,e.mode)
|
|
2149
|
-
r.replacements=c,r.successfulReplacements=c.filter((e=>e.success)).length,r.failedReplacements=c.filter((e=>!e.success)).length,a!==i?(await l.default.writeFile(o,a,"utf8"),t.documentFileManager.markForSync(e.documentId),r.success=!0,L++,y.info("Document updated successfully",{documentId:e.documentId,filename:r.filename,successfulReplacements:r.successfulReplacements,failedReplacements:r.failedReplacements})):0===r.failedReplacements&&(r.success=!0),N+=r.failedReplacements}catch(t){r.error=(0,m.getErrorMessage)(t),r.failedReplacements=e.replacements.length,N+=r.failedReplacements,y.error("Document operation failed",{documentId:e.documentId,error:r.error})}F.push(r)}if(
|
|
2150
|
-
r?.success&&await t.documentFileManager.syncDocument(e.documentId)}}catch(e){y.warn("Some documents may not have synced properly",{error:e})}const z=await d.handleMultiFileGitCommit(C,T,F,L,{operationType:"Replace strings",toolRecordId:b,successField:"successfulReplacements",logger:y,metrics:a,metricsPrefix:"replace_strings"},t),B=d.processMultiFileOperationResults(F,"successfulReplacements"),{successfulOperations:H,failedOperations:U,totalSuccessfulChanges:
|
|
2151
|
-
try{await o.updateToolRecord(b,{metadata:{path:T.length>0?T[0].path:"document:"+
|
|
2083
|
+
r.replacements=c,r.successfulReplacements=c.filter((e=>e.success)).length,r.failedReplacements=c.filter((e=>!e.success)).length,a!==i?(await l.default.writeFile(o,a,"utf8"),t.documentFileManager.markForSync(e.documentId),r.success=!0,L++,y.info("Document updated successfully",{documentId:e.documentId,filename:r.filename,successfulReplacements:r.successfulReplacements,failedReplacements:r.failedReplacements})):0===r.failedReplacements&&(r.success=!0),N+=r.failedReplacements}catch(t){r.error=(0,m.getErrorMessage)(t),r.failedReplacements=e.replacements.length,N+=r.failedReplacements,y.error("Document operation failed",{documentId:e.documentId,error:r.error})}F.push(r)}if(R.length>0)try{for(const e of R){const r=F.find((t=>t.documentId===e.documentId))
|
|
2084
|
+
r?.success&&await t.documentFileManager.syncDocument(e.documentId)}}catch(e){y.warn("Some documents may not have synced properly",{error:e})}const z=await d.handleMultiFileGitCommit(C,T,F,L,{operationType:"Replace strings",toolRecordId:b,successField:"successfulReplacements",logger:y,metrics:a,metricsPrefix:"replace_strings"},t),B=d.processMultiFileOperationResults(F,"successfulReplacements"),{successfulOperations:H,failedOperations:U,totalSuccessfulChanges:G,overallSuccess:W,successfulFiles:V,failedFiles:J}=B
|
|
2085
|
+
try{await o.updateToolRecord(b,{metadata:{path:T.length>0?T[0].path:"document:"+R[0]?.documentId,status:W?"completed":"failed",error:W?void 0:U+" operations failed",totalOperations:F.length,successfulFiles:V,failedFiles:J,operations:D,totalSuccessfulReplacements:G,totalFailedReplacements:N,operationsWithChanges:L,processingTime:Date.now()-w,userComment:E,...T.length>0&&z.success&&z.commitHash&&{commitHash:z.commitHash,previousCommitHash:z.previousCommitHash||void 0}},note:W?`String replacement completed: ${H}/${F.length} operations successful${T.length>0?" (committed to git)":""}`:`String replacement partially failed: ${U}/${F.length} operations failed`})}catch(e){y.warn("Failed to update tool record",{recordError:e})}d.formatMultiFileToolResponse("String Replacement",{successfulOperations:H,failedOperations:U,totalSuccessfulChanges:G,overallSuccess:W,successfulFiles:V,failedFiles:J},z,$)
|
|
2152
2086
|
let K="## String Replacement Results\n\n"
|
|
2153
|
-
if(t.workspaceManager&&(K+=`**Branch:** \`${t.workspaceManager.getCurrentContext().branchName}\`\n\n`),K+="**Summary:**\n",K+=`- **Files processed:** ${H+U}\n`,K+=`- **Successful operations:** ${H}\n`,K+=`- **Failed operations:** ${U}\n`,K+=`- **Total replacements:** ${
|
|
2087
|
+
if(t.workspaceManager&&(K+=`**Branch:** \`${t.workspaceManager.getCurrentContext().branchName}\`\n\n`),K+="**Summary:**\n",K+=`- **Files processed:** ${H+U}\n`,K+=`- **Successful operations:** ${H}\n`,K+=`- **Failed operations:** ${U}\n`,K+=`- **Total replacements:** ${G} successful, ${N} failed\n\n`,z.success&&z.commitHash&&(K+="**Git Commit:**\n",K+=`- **Commit Hash:** ${z.commitHash.substring(0,8)}\n`,K+=`- **Files Committed:** ${z.filesCommitted.length}\n`,z.previousCommitHash&&(K+=`- **Previous Commit:** ${z.previousCommitHash.substring(0,8)}\n`),K+="\n"),$.lockAcquired&&$.lockedRequestId&&(K+=`\u{1f512} **Locked request:** ${$.lockedRequestId}\n\n`),1===F.length){const e=F[0]
|
|
2154
2088
|
if(K+=`**Operation:** ${e.success?"\u2705 Success":"\u274c Failed"}\n`,"file"===e.type?K+=`**File:** ${e.path}\n`:(K+="**Document:** "+e.documentId,e.filename&&(K+=` (${e.filename})`),K+="\n"),e.error?K+=`**Error:** ${e.error}\n`:(K+=`**Replacements:** ${e.successfulReplacements} successful`,e.failedReplacements>0&&(K+=`, ${e.failedReplacements} failed`),K+="\n"),e.replacements.some((e=>!e.success))){K+="**Failed Replacement Details:**\n"
|
|
2155
|
-
for(const t of e.replacements.filter((e=>!e.success)))K+=`- "${t.old_str}" \u2192 "${t.new_str}": ${t.error}\n`}}else{K+="**Summary:**\n",K+=`- **Total Operations:** ${F.length}\n`,K+=`- **Successful:** ${H}\n`,K+=`- **Failed:** ${U}\n`,K+=`- **Total Replacements:** ${
|
|
2089
|
+
for(const t of e.replacements.filter((e=>!e.success)))K+=`- "${t.old_str}" \u2192 "${t.new_str}": ${t.error}\n`}}else{K+="**Summary:**\n",K+=`- **Total Operations:** ${F.length}\n`,K+=`- **Successful:** ${H}\n`,K+=`- **Failed:** ${U}\n`,K+=`- **Total Replacements:** ${G} successful, ${N} failed\n\n`,K+="**Detailed Results:**\n\n"
|
|
2156
2090
|
for(const e of F){if("file"===e.type?K+=`### File: ${e.path}\n`:(K+="### Document: "+e.documentId,e.filename&&(K+=` (${e.filename})`),K+="\n"),K+=`- **Status:** ${e.success?"\u2705 Success":"\u274c Failed"}\n`,e.error?K+=`- **Error:** ${e.error}\n`:(K+=`- **Replacements:** ${e.successfulReplacements} successful`,e.failedReplacements>0&&(K+=`, ${e.failedReplacements} failed`),K+="\n"),e.replacements.some((e=>!e.success))){K+="- **Failed Replacement Details:**\n"
|
|
2157
|
-
for(const t of e.replacements.filter((e=>!e.success)))K+=` - "${t.old_str}" \u2192 "${t.new_str}": ${t.error}\n`}K+="\n"}}
|
|
2091
|
+
for(const t of e.replacements.filter((e=>!e.success)))K+=` - "${t.old_str}" \u2192 "${t.new_str}": ${t.error}\n`}K+="\n"}}R.length>0&&(K+="\u{1f4c4} **Document Changes:** Modified documents have been automatically synced back to the tracking system.\n\n")
|
|
2158
2092
|
const Y=Date.now()-w
|
|
2159
|
-
return y.info("Replace strings operation completed",{duration:Y,success:
|
|
2093
|
+
return y.info("Replace strings operation completed",{duration:Y,success:W,totalOperations:F.length,successfulOperations:H,failedOperations:U}),a.incrementCounter("replace_strings_total",1,{success:W}),{content:[{type:"text",text:K}],isError:!W}}catch(t){const r=Date.now()-w
|
|
2160
2094
|
if(y.error("Replace strings operation failed",{error:t instanceof Error?t.stack:t+"",duration:r,phase:I}),b)try{await o.updateToolRecord(b,{metadata:{path:e?.operations?.[0]?.path||e?.operations?.[0]?.documentId,status:"failed",error:(0,m.getErrorMessage)(t),phase:I,duration:r,userComment:e?.comment},note:"String replacement failed: "+(0,m.getErrorMessage)(t)})}catch(e){}return a.incrementCounter("replace_strings_errors",1,{phase:I}),{content:[{type:"text",text:"\u274c **Replace Strings Failed:** "+(0,m.getErrorMessage)(t)}],isError:!0}}}
|
|
2161
2095
|
const l=c(t(1943)),u=t(6183),d=a(t(5967)),h=t(9860),g=t(5003),p=t(7478),f=t(9949),m=t(8824)},3322(e,exports,t){"use strict"
|
|
2162
2096
|
var r,n=this&&this.__createBinding||(Object.create?function(e,t,r,n){void 0===n&&(n=r)
|
|
@@ -2366,17 +2300,17 @@ if(T=e.id,f.info("Created task",{taskId:T}),f.debug("Executing file operation",{
|
|
|
2366
2300
|
else if("replace"===t)v=await(0,o.handleReplaceInFiles)({taskId:T,...C,comment:_},u,w,b,y,h,g,p)
|
|
2367
2301
|
else{if("manage"!==t)throw new r.ValidationError("Unsupported operation type: "+t)
|
|
2368
2302
|
v=await(0,s.handleManageFiles)({taskId:T,...C,comment:_||I},u,w,b,y,d,h,g,p)}if(v.isError){f.error("File operation failed, cleaning up request and task",{requestId:S,taskId:T})
|
|
2369
|
-
try{await w.updateTaskStatus(T,"canceled"),f.info("Canceled task after operation failure",{taskId:T})}catch(e){f.warn("Failed to cancel task during cleanup",{taskId:T,error:e instanceof Error?e.message:e+""})}try{await y.updateRequest(S,{status:"canceled"}),f.info("Canceled request after operation failure",{requestId:S}),u.workspaceManager&&(await u.workspaceManager.cancelRequest(S),f.info("Cleaned up branch/worktree after operation failure",{requestId:S}))}catch(e){f.warn("Failed to cancel request during cleanup",{requestId:S,error:e instanceof Error?e.message:e+""})}return{content:[{type:"text",text:`\u274c Quick change failed during ${t} operation:\n\n${v.content[0].text}\n\nThe request (${S}) and task have been canceled and cleaned up.`}],isError:!0}}const q=v.content[0].text,
|
|
2370
|
-
|
|
2371
|
-
try{await(0,i.handleCompleteTask)({taskId:T,summary:`Executed ${t} operation for quick fix: ${I}${
|
|
2303
|
+
try{await w.updateTaskStatus(T,"canceled"),f.info("Canceled task after operation failure",{taskId:T})}catch(e){f.warn("Failed to cancel task during cleanup",{taskId:T,error:e instanceof Error?e.message:e+""})}try{await y.updateRequest(S,{status:"canceled"}),f.info("Canceled request after operation failure",{requestId:S}),u.workspaceManager&&(await u.workspaceManager.cancelRequest(S),f.info("Cleaned up branch/worktree after operation failure",{requestId:S}))}catch(e){f.warn("Failed to cancel request during cleanup",{requestId:S,error:e instanceof Error?e.message:e+""})}return{content:[{type:"text",text:`\u274c Quick change failed during ${t} operation:\n\n${v.content[0].text}\n\nThe request (${S}) and task have been canceled and cleaned up.`}],isError:!0}}const q=v.content[0].text,R=q.includes("\u26a0\ufe0f Partial Success")||q.includes("\u274c Failed")||q.includes("\u274c 0 successful")
|
|
2304
|
+
R?f.warn("File operation completed with partial failures",{requestId:S}):f.info("File operation completed successfully"),f.debug("Completing task")
|
|
2305
|
+
try{await(0,i.handleCompleteTask)({taskId:T,summary:`Executed ${t} operation for quick fix: ${I}${R?" (partial success)":""}`},u,d,h,g),f.info("Task completed successfully",{taskId:T})}catch(e){f.error("Task completion via handleCompleteTask failed, attempting direct status update",{taskId:T,error:e instanceof Error?e.message:e+"",errorStack:e instanceof Error?e.stack:void 0})
|
|
2372
2306
|
try{await w.updateTaskStatus(T,"completed"),f.info("Task completed via direct updateTaskStatus call",{taskId:T})}catch(e){return f.error("Direct task completion ALSO failed - task may be stuck in in_progress",{taskId:T,error:e instanceof Error?e.message:e+"",errorStack:e instanceof Error?e.stack:void 0,operationType:t,isDocumentOperation:!!C.documentId}),{content:[{type:"text",text:`\u26a0\ufe0f Quick change operation succeeded but task completion failed.\n\n**Request:** ${S}\n**Task:** ${T}\n**Issue:** Could not mark task as completed - it remains in 'in_progress' state\n\nThe ${t} operation was successful, but we couldn't automatically complete the task. Please use the complete-task tool manually with taskId: ${T}\n\nError: `+(e instanceof Error?e.message:e+"")}],isError:!0}}}f.debug("Completing request")
|
|
2373
|
-
const R
|
|
2307
|
+
const P=R?`Quick change completed with partial success: ${I}. Some replacements failed - see details below.`:"Quick change completed: "+I,M=R?t+" operation partially completed - some operations succeeded, some failed":t+" operation executed successfully"
|
|
2374
2308
|
let x=!1
|
|
2375
|
-
try{const e=await(0,a.handleCompleteRequest)({requestId:S,summary:
|
|
2309
|
+
try{const e=await(0,a.handleCompleteRequest)({requestId:S,summary:P,acceptanceEvidence:[{evidence:M}],testVerification:void 0},u,d,h,g,p)
|
|
2376
2310
|
if(e.isError)f.error("Request completion failed, attempting direct completion",{requestId:S,error:e.content[0].text})
|
|
2377
|
-
else{try{await y.updateRequest(S,{status:"completed",completionSummary:
|
|
2378
|
-
let
|
|
2379
|
-
return f.info("Quick fix completed",{requestId:S,duration:
|
|
2311
|
+
else{try{await y.updateRequest(S,{status:"completed",completionSummary:P}),f.info("Request finalized to completed",{requestId:S})}catch(e){f.warn("Failed to finalize request to completed, may be stuck at ready_for_merge",{requestId:S,error:(0,l.getErrorMessage)(e)})}x=!0,f.info("Request completed successfully",{requestId:S})}}catch(e){f.error("Request completion threw exception, attempting direct completion",{requestId:S,error:e instanceof Error?e.message:e+""})}if(!x)try{f.info("Attempting direct request completion via API",{requestId:S}),await y.updateRequest(S,{status:"completed",completionSummary:P}),x=!0,f.info("Request completed successfully via direct API call",{requestId:S})}catch(e){return f.error("Direct request completion also failed",{requestId:S,error:e instanceof Error?e.message:e+""}),{content:[{type:"text",text:`\u26a0\ufe0f Quick change operation succeeded but request completion failed.\n\n**Request:** ${S}\n**Status:** Still in 'in_progress' - please complete manually\n\nThe file operation was successful, but we couldn't automatically complete the request. Please use the complete-request tool manually.`}],isError:!0}}const j=Date.now()-m
|
|
2312
|
+
let O
|
|
2313
|
+
return f.info("Quick fix completed",{requestId:S,duration:j,hasPartialFailure:R}),O=R?`\u26a0\ufe0f Quick change completed with partial success\n\n**Request:** ${S}\n**Title:** ${I}\n**Operation:** ${t}\n**Duration:** ${j}ms\n**Status:** Some operations succeeded, some failed\n\nThe successful changes have been applied and automatically merged to main.\n**Active branch:** main\n\n**\u26a0\ufe0f Note:** This quick-fix had partial failures. See operation details below:\n\n`+q:`\u2705 Quick change completed successfully!\n\n**Request:** ${S}\n**Title:** ${I}\n**Operation:** ${t}\n**Duration:** ${j}ms\n\nThe change has been applied and automatically merged to main.\n**Active branch:** main`+(q.match(/\[RECORD:trec\d{6}\]/)?.[0]?"\n"+q.match(/\[RECORD:trec\d{6}\]/)?.[0]:""),E&&(O+="\n\n\u{1f4a1} **Recommendation:** You've created several quick-edits in a row. For better traceability and organization, consider creating a proper feature or bugfix request with multiple tasks for your next change."),{content:[{type:"text",text:O}]}}catch(e){if(f.error("Quick change workflow failed after request creation, cleaning up",{requestId:S,error:(0,l.getErrorMessage)(e)}),T)try{await w.updateTaskStatus(T,"canceled"),f.info("Canceled task after workflow failure",{taskId:T})}catch(e){f.warn("Failed to cancel task during cleanup",{taskId:T,error:e instanceof Error?e.message:e+""})}try{await y.updateRequest(S,{status:"canceled"}),f.info("Canceled request after workflow failure",{requestId:S}),u.workspaceManager&&(await u.workspaceManager.cancelRequest(S),f.info("Cleaned up branch/worktree after workflow failure",{requestId:S}))}catch(e){f.warn("Failed to cancel request during cleanup",{requestId:S,error:e instanceof Error?e.message:e+""})}throw e}}catch(e){const t=Date.now()-m
|
|
2380
2314
|
return f.error("Quick change failed",{error:(0,l.getErrorMessage)(e),duration:t}),e instanceof r.ValidationError?{content:[{type:"text",text:"\u274c "+e.message}],isError:!0}:{content:[{type:"text",text:"\u274c Quick change failed: "+(0,l.getErrorMessage)(e)}],isError:!0}}}
|
|
2381
2315
|
const r=t(9860),n=t(4079),o=t(9442),s=t(7684),i=t(355),a=t(5715),c=t(7478),l=t(8824)},3807(module){"use strict"
|
|
2382
2316
|
module.exports=require("simple-git")},3895(e,exports,t){"use strict"
|
|
@@ -2445,49 +2379,49 @@ return o(t,e),t}),i=this&&this.__importDefault||function(e){return e&&e.__esModu
|
|
|
2445
2379
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.handleWriteFile=async function(e,t,r,n,o,s,i,m,y){const w=i.child({tool:"write_file"}),k=m.startTimer("tool_execution_time"),b=Date.now()
|
|
2446
2380
|
let I,v,C=u.FileOperationPhase.VALIDATION
|
|
2447
2381
|
const _={toolName:"write_file",operationName:"write",fileOperationPhase:u.FileOperationPhase.FILE_WRITE,recordType:"write-file",metricsPrefix:"write_file",successMessage:"Successfully wrote content",failureMessage:"Failed to write content"}
|
|
2448
|
-
try{const r=u.validateArgs(e,l.WriteFileSchema),{taskId:i,path:f,documentId:E,content:q,format:S,append:T,comment:
|
|
2449
|
-
w.info("Writing content to "+(
|
|
2450
|
-
let x,O
|
|
2451
|
-
const F=
|
|
2452
|
-
if(
|
|
2382
|
+
try{const r=u.validateArgs(e,l.WriteFileSchema),{taskId:i,path:f,documentId:E,content:q,format:S,append:T,comment:R}=r,P=!!E,M=!!f
|
|
2383
|
+
w.info("Writing content to "+(P?"document":"file"),{taskId:i,filePath:M?f:void 0,documentId:P?E:void 0,contentLength:"string"==typeof q?q.length:JSON.stringify(q).length,format:S,append:T,comment:R})
|
|
2384
|
+
let x,j,O,$="",D=!1,A=!1
|
|
2385
|
+
const F=M?f:void 0
|
|
2386
|
+
if(P){if(t.apiClient)try{await(0,p.ensureDocumentNotLocked)(E,t.apiClient,w,m,"write_file-document")}catch(e){if(e instanceof d.ValidationError)return{content:[{type:"text",text:e.message}],isError:!0}
|
|
2453
2387
|
throw e}if(!t.documentFileManager)throw Error("Document file manager not available")
|
|
2454
2388
|
$=await t.documentFileManager.getDocumentAsFile(E)
|
|
2455
2389
|
const e=t.documentFileManager.getCachedDocumentInfo(E)
|
|
2456
|
-
|
|
2457
|
-
const N=
|
|
2390
|
+
O=e?.filename,A=!0,D=!1}C=u.FileOperationPhase.TASK_VALIDATION,m.incrementCounter("write_file_phase",1,{phase:C})
|
|
2391
|
+
const N=M?F:"document:"+E,L=await u.validateTaskId(i,N,n,w,m,_.metricsPrefix),z=L?.requestId
|
|
2458
2392
|
let B=null
|
|
2459
|
-
|
|
2393
|
+
M&&z&&(B=await u.validateWorkItemStates(i,N,n,s,t,w,m,_.metricsPrefix))
|
|
2460
2394
|
let H={taskPromoted:!1,requestPromoted:!1}
|
|
2461
|
-
|
|
2462
|
-
const U=await u.ensureCorrectWorkspaceContext({taskPromoted:H.taskPromoted,requestId:z,context:t,operation:"write_file",logger:w,metrics:m,metricsPrefix:_.metricsPrefix,requireRequestContext:
|
|
2395
|
+
M&&z&&B&&(H=await u.autoPromoteTaskStatus(i,L.status,z,B.request?.status,N,n,s,w,m,_.metricsPrefix),H.taskPromoted&&w.info("Auto-promoted task to in_progress for file operation",{taskId:i,requestId:z,previousStatus:L.status,newStatus:H.newTaskStatus,triggeringOperation:"write_file"}))
|
|
2396
|
+
const U=await u.ensureCorrectWorkspaceContext({taskPromoted:H.taskPromoted,requestId:z,context:t,operation:"write_file",logger:w,metrics:m,metricsPrefix:_.metricsPrefix,requireRequestContext:M})
|
|
2463
2397
|
if(!U.success){if(U.isLockConflict)return{content:[{type:"text",text:"\u274c "+U.error}],isError:!0}
|
|
2464
|
-
throw Error(U.error)}if(U.switched&&w.info("Workspace context successfully established",{requestId:z,branchName:U.branchName,operation:"write_file"}),
|
|
2465
|
-
x=e.normalizedPath,
|
|
2466
|
-
try{await c.default.access(
|
|
2398
|
+
throw Error(U.error)}if(U.switched&&w.info("Workspace context successfully established",{requestId:z,branchName:U.branchName,operation:"write_file"}),M&&F){const e=u.validateAndNormalizePath(F,t)
|
|
2399
|
+
x=e.normalizedPath,j=e.fullPath,$=j
|
|
2400
|
+
try{await c.default.access(j),A=!0}catch{A=!1,D=!0}w.debug("Path validated with correct workspace context",{rawPath:F,normalizedPath:x,fullPath:j,workspaceBasePath:t.workspaceManager?.getCurrentContext().basePath})}if(P&&z)try{await(0,h.validateRequestStatusForDocumentOperation)(z,s,w,m,"write_file-document")}catch(e){if(e instanceof d.ValidationError)return{content:[{type:"text",text:e.message}],isError:!0}
|
|
2467
2401
|
throw e}C=u.FileOperationPhase.RECORD_CREATION,m.incrementCounter("write_file_phase",1,{phase:C})
|
|
2468
|
-
const{toolRecordId:
|
|
2469
|
-
let
|
|
2470
|
-
if(I=
|
|
2471
|
-
else
|
|
2472
|
-
let V=
|
|
2473
|
-
if(
|
|
2402
|
+
const{toolRecordId:G}=await u.createFileOperationRecords(i,z,t.projectId,_.recordType,N,{operationType:P?"document":"file",documentId:P?E:void 0,documentFilename:O,filePath:M?x:void 0,contentLength:"string"==typeof q?q.length:JSON.stringify(q).length,format:S||"text",append:T||!1,wasFileCreated:!A,userComment:R},n,o,w,m,_.metricsPrefix,y)
|
|
2403
|
+
let W
|
|
2404
|
+
if(I=G,v=G,C=_.fileOperationPhase,m.incrementCounter("write_file_phase",1,{phase:C}),"json"===S)if("string"==typeof q)try{JSON.parse(q),W=q}catch(e){throw new d.ValidationError("Content is not valid JSON")}else W=JSON.stringify(q,null,2)
|
|
2405
|
+
else W="string"==typeof q?q:JSON.stringify(q,null,2)
|
|
2406
|
+
let V=W
|
|
2407
|
+
if(M&&t.git)try{w.debug("[WRITE-FILE] Checking for user changes before write operation")
|
|
2474
2408
|
const e=await(0,g.commitUserChangesBeforeToolOperation)(t.git,"write_file",{requestId:t.workspaceManager?.getCurrentContext()?.requestId,taskId:i},w,m)
|
|
2475
2409
|
e.userChangesCommitted&&(w.debug("[WRITE-FILE] User changes committed before write operation",{commitHash:e.commitHash?.substring(0,8),filesCommitted:e.filesCommitted}),w.info("User changes committed before write-file operation",{taskId:i,path:x,userCommitHash:e.commitHash?.substring(0,8),userFilesCommitted:e.filesCommitted}))}catch(e){w.debug("[WRITE-FILE] Pre-tool commit failed, continuing with write",{error:e instanceof Error?e.message:e+""}),w.warn("Pre-tool user changes commit failed, continuing with write operation",{taskId:i,path:x,error:e instanceof Error?e.message:e+""})}if(!$)throw Error("Target path not properly initialized")
|
|
2476
|
-
if(w.debug("[WRITE-FILE] Proceeding with file write operation",{targetPath:$}),T&&A)try{V=await c.default.readFile($,"utf8")+
|
|
2477
|
-
if(await c.default.mkdir(J,{recursive:!0}),await c.default.writeFile($,V,"utf8"),w.info("Content written successfully",{path:
|
|
2410
|
+
if(w.debug("[WRITE-FILE] Proceeding with file write operation",{targetPath:$}),T&&A)try{V=await c.default.readFile($,"utf8")+W}catch(e){w.warn("Failed to read existing content for append",{error:e})}const J=a.default.dirname($)
|
|
2411
|
+
if(await c.default.mkdir(J,{recursive:!0}),await c.default.writeFile($,V,"utf8"),w.info("Content written successfully",{path:M?x:"document:"+E,finalLength:V.length,append:T,wasCreated:D}),P){t.documentFileManager.markForSync(E)
|
|
2478
2412
|
try{await t.documentFileManager.syncDocument(E),w.info("Document synced successfully",{documentId:E})}catch(e){w.warn("Failed to sync document immediately",{documentId:E,error:e})}}let K,Y,Q=null
|
|
2479
|
-
if(
|
|
2413
|
+
if(M){if(C=u.FileOperationPhase.GIT_COMMIT,m.incrementCounter("write_file_phase",1,{phase:C}),t.workspaceManager){const e=t.workspaceManager.getCurrentContext()
|
|
2480
2414
|
Y=e.branchName,w.debug("Retrieved branch name from workspace manager",{branchName:Y,requestId:e.requestId,mode:e.mode,isMainBranch:e.isMainBranch})}try{const e=`${D?"Create":T?"Append to":"Update"} ${x} (${v})`,r=await u.commitToGit(i,x,v,v,e,t,w,m,_.metricsPrefix)
|
|
2481
|
-
K=r.commitHash,Q=r.previousCommitHash,w.info("Changes committed to git via shared utility",{path:x,commitMessage:e,commitHash:K?.substring(0,8),previousCommitHash:Q?.substring(0,8),branchName:Y,toolRecordId:v})}catch(e){w.warn("Git operations failed via shared utility",{error:e})}}try{await o.updateToolRecord(v,{metadata:{path:
|
|
2482
|
-
Z+=`**Content Length:** ${V.length} characters\n`,
|
|
2415
|
+
K=r.commitHash,Q=r.previousCommitHash,w.info("Changes committed to git via shared utility",{path:x,commitMessage:e,commitHash:K?.substring(0,8),previousCommitHash:Q?.substring(0,8),branchName:Y,toolRecordId:v})}catch(e){w.warn("Git operations failed via shared utility",{error:e})}}try{await o.updateToolRecord(v,{metadata:{path:M?x:"document:"+E,status:"completed",finalContentLength:V.length,wasFileCreated:D,wasAppended:T&&A,operationType:P?"document":"file",processingTime:Date.now()-b,userComment:R,...M&&K&&{commitHash:K,previousCommitHash:Q||void 0}},note:"Write operation completed successfully"+(P?" (document synced)":" (committed to git)")})}catch(e){w.warn("Failed to update tool record",{recordError:e})}let Z=`**${D?"Created":T?"Appended to":"Updated"} ${P?`document ${E}${O?` (${O})`:""}`:"file "+x}**\n`
|
|
2416
|
+
Z+=`**Content Length:** ${V.length} characters\n`,M&&Y&&(Z+=`**Branch:** ${Y}\n`),U.lockAcquired&&U.lockedRequestId&&(Z+=`**Locked request:** ${U.lockedRequestId}\n`),M&&K&&(Z+=`**Commit Hash:** ${K.substring(0,8)}\n`,Q&&(Z+=`**Previous Commit:** ${Q.substring(0,8)}\n`)),v&&(Z+=`[RECORD:${v}]\n`),P&&(Z+=`\n**Document Update:** The document content has been updated and synced back to the tracking system. You can continue editing using other file modification tools with documentId \`${E}\`.`)
|
|
2483
2417
|
const X=Date.now()
|
|
2484
|
-
return w.info("Write operation completed successfully",{duration:X-b,path:
|
|
2418
|
+
return w.info("Write operation completed successfully",{duration:X-b,path:M?x:"document:"+E,contentLength:V.length,wasCreated:D}),k({tool:"write_file",success:!0}),m.incrementCounter("write_file_total",1,{success:!0}),t.workspaceManager?.largeFileWarning&&(Z+=t.workspaceManager.largeFileWarning,t.workspaceManager.largeFileWarning=""),{content:[{type:"text",text:Z}]}}catch(t){const r=Date.now()-b
|
|
2485
2419
|
if(w.error("Write operation failed",{error:t instanceof Error?t.stack:t+"",duration:r,phase:C}),v)try{await o.updateToolRecord(v,{metadata:{path:e?.path,status:"failed",error:(0,f.getErrorMessage)(t),phase:C,duration:r,userComment:e?.comment},note:"Write operation failed: "+(0,f.getErrorMessage)(t)})}catch(e){}return k({tool:"write_file",success:!1}),m.incrementCounter("write_file_errors",1,{phase:C}),{content:[{type:"text",text:"\u274c **Write Operation Failed:** "+(0,f.getErrorMessage)(t)}],isError:!0}}}
|
|
2486
2420
|
const a=i(t(6928)),c=i(t(1943)),l=t(6183),u=s(t(5967)),d=t(9860),h=t(5003),g=t(7478),p=t(9949),f=t(8824)},4139(e,exports){"use strict"
|
|
2487
2421
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.ALCHEMY_DIR_NAME=exports.TOKEN_DIR_NAME=void 0,exports.TOKEN_DIR_NAME="alchemy-key",exports.ALCHEMY_DIR_NAME=".alchemy_lab"},4165(e,exports,t){"use strict"
|
|
2488
2422
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.def=void 0
|
|
2489
2423
|
const r=t(6183),n=t(4648)
|
|
2490
|
-
exports.def={name:"request_operations",description:"Perform operations on existing requests.\n\nOperations:\n\u2022 complete - Begin completion: provide summary, get criteria keys for verification\n\u2022 verify-criteria - Verify acceptance criteria with evidence per key (triggers merge when all verified)\n\u2022 finalize - Approve and merge a request that is ready for review\n\u2022 approve - Approve a pending request so work can begin\n\u2022 revert - Completely revert a completed request, undoing all changes\n\u2022 get-info - Get comprehensive request information\n\u2022 list - List and filter requests\n\nCompletion is two-phase: first call complete with a summary, then call verify-criteria with evidence for each criterion key.\n\nNote: To create a new request, use the separate create-request tool.",schema:r.RequestOperationsSchema,annotations:{title:"Request Operations",readOnlyHint:!1,destructiveHint:!0,idempotentHint:!1},handler(e,t){return(0,n.handleRequestOperations)(e,t.context,t.apiClient,t.logger,t.metrics,t.mcpServer)}}},4192(e,exports,t){"use strict"
|
|
2424
|
+
exports.def={name:"request_operations",description:"Perform operations on existing requests.\n\nOperations:\n\u2022 complete - Begin completion: provide summary, get criteria keys for verification\n\u2022 verify-criteria - Verify acceptance criteria with evidence per key (triggers merge when all verified)\n\u2022 finalize - Approve and merge a request that is ready for review\n\u2022 approve - Approve a pending request so work can begin\n\u2022 revert - Completely revert a completed request, undoing all changes\n\u2022 get-info - Get comprehensive request information\n\u2022 list - List and filter requests\n\u2022 delete-empty - Delete a request that has no tasks (safe cleanup for mistaken or obsolete requests)\n\nCompletion is two-phase: first call complete with a summary, then call verify-criteria with evidence for each criterion key.\n\nNote: To create a new request, use the separate create-request tool.",schema:r.RequestOperationsSchema,annotations:{title:"Request Operations",readOnlyHint:!1,destructiveHint:!0,idempotentHint:!1},handler(e,t){return(0,n.handleRequestOperations)(e,t.context,t.apiClient,t.logger,t.metrics,t.mcpServer)}}},4192(e,exports,t){"use strict"
|
|
2491
2425
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.BaseApiClient=void 0
|
|
2492
2426
|
const r=t(7163)
|
|
2493
2427
|
exports.BaseApiClient=class{constructor(e,t,n,o,s){this.failureCount=0,this.circuitState="closed",this.circuitResetTimeout=null,this.baseUrl=e,this.logger=t,this.metrics=n,this.authToken=o,this.options={retryAttempts:3,retryDelay:1e3,timeout:1e4,circuitBreakerThreshold:5,circuitBreakerResetTime:3e4,...s},this.logger.debug("BaseApiClient constructor options:",{providedOptions:s?JSON.stringify(s):"undefined",mergedOptions:JSON.stringify(this.options)})
|
|
@@ -2684,21 +2618,23 @@ return p.error("Recovery operation failed",{error:e instanceof Error?e.stack:e+"
|
|
|
2684
2618
|
const i=t(6183),a=t(1569),c=s(t(6928)),l=s(t(1943)),u=s(t(5967)),d=t(3922),h=t(8824)},4648(e,exports,t){"use strict"
|
|
2685
2619
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.handleRequestOperations=async function(e,t,d,h,g,p){const f=h.child({tool:"request_operations"})
|
|
2686
2620
|
try{for(const t of["complete","verifyCriteria","merge","revert","search","list"])if(e&&"string"==typeof e[t])try{e[t]=JSON.parse(e[t])}catch{}"complete"===e?.operation&&e?.summary&&!e?.complete&&(e.complete={summary:e.summary},delete e.summary),"complete"!==e?.operation||e?.complete||e?.summary||(e.complete={summary:""}),"merge"===e?.operation&&e?.verifications&&!e?.merge&&(e.merge={verifications:e.verifications},delete e.verifications),e?.merge&&Array.isArray(e.merge)&&(e.merge={verifications:e.merge}),"verify-criteria"===e?.operation&&(e.operation="merge",e.verifyCriteria&&!e.merge&&(e.merge=e.verifyCriteria,delete e.verifyCriteria)),"finalize"===e?.operation&&(e.operation="merge",e.merge||(e.merge={verifications:[]})),"revert"===e?.operation&&e?.reason&&!e?.revert&&(e.revert={reason:e.reason,confirmDestructive:e.confirmDestructive},delete e.reason,delete e.confirmDestructive),"search"===e?.operation&&e?.query&&!e?.search&&(e.search={query:e.query,searchIn:e.searchIn||"all",filters:e.filters},delete e.query,delete e.searchIn,delete e.filters)
|
|
2687
|
-
const
|
|
2688
|
-
switch(f.info("Processing request operation",{requestId:
|
|
2689
|
-
const e={requestId:
|
|
2690
|
-
return await(0,n.handleCompleteRequest)(e,t,d,h,g,p)}case"merge":return f.info("Routing to merge handler"),await(0,l.handleMergeRequest)({requestId:
|
|
2621
|
+
const m=r.RequestOperationsSchema.parse(e),{requestId:y,operation:w}=m
|
|
2622
|
+
switch(f.info("Processing request operation",{requestId:y,operation:w}),w){case"complete":{f.info("Routing to complete-request handler")
|
|
2623
|
+
const e={requestId:y,summary:m.complete.summary}
|
|
2624
|
+
return await(0,n.handleCompleteRequest)(e,t,d,h,g,p)}case"merge":return f.info("Routing to merge handler"),await(0,l.handleMergeRequest)({requestId:y,verifications:m.merge?.verifications||[]},t,d,h,g,p)
|
|
2691
2625
|
case"approve":{f.info("Routing to approve-request handler")
|
|
2692
|
-
const e={requestId:
|
|
2626
|
+
const e={requestId:y}
|
|
2693
2627
|
return await(0,c.handleApproveRequest)(e,t,d,h,g,p)}case"revert":{f.info("Routing to revert-request handler")
|
|
2694
|
-
const e={requestId:
|
|
2628
|
+
const e={requestId:y,reason:m.revert.reason,confirmDestructive:m.revert.confirmDestructive}
|
|
2695
2629
|
return await(0,o.handleRevertRequest)(e,t,d,h,g)}case"get-info":{f.info("Routing to get-request-information handler")
|
|
2696
|
-
const e={requestId:
|
|
2630
|
+
const e={requestId:y}
|
|
2697
2631
|
return await(0,s.handleGetRequestInformation)(e,t,d,h,g)}case"list":{f.info("Routing to list-requests handler")
|
|
2698
|
-
const e={filters:
|
|
2632
|
+
const e={filters:m.list?.filters}
|
|
2699
2633
|
return await(0,i.handleListRequests)(e,t,d,h,g)}case"search":{f.info("Routing to search-requests handler")
|
|
2700
|
-
const e={search:
|
|
2701
|
-
return await(0,a.handleSearchRequests)(e,t,d,h,g)}
|
|
2634
|
+
const e={search:m.search}
|
|
2635
|
+
return await(0,a.handleSearchRequests)(e,t,d,h,g)}case"delete-empty":if(f.info("Routing to delete-empty handler"),!y)return{content:[{type:"text",text:"\u274c **Request Operations Failed:** requestId is required for delete-empty"}],isError:!0}
|
|
2636
|
+
try{const e=d.getProxyClient(),r=await e.proxyGet(`/api/projects/${t.projectId}/tasks`,{requestLocalId:y,limit:1}),n=r?.data||r||[]
|
|
2637
|
+
return(Array.isArray(n)?n.length:0)>0?{content:[{type:"text",text:`\u274c Cannot delete ${y}: it has tasks. Only empty requests (no tasks created) can be deleted.`}],isError:!0}:(await e.proxyDelete(`/api/projects/${t.projectId}/requests/${y}`),f.info("Empty request deleted",{requestId:y}),{content:[{type:"text",text:`\u2705 Request ${y} deleted (had no tasks).`}]})}catch(e){return{content:[{type:"text",text:"\u274c **Failed to delete request:** "+(0,u.getErrorMessage)(e)}],isError:!0}}default:{const e="Unknown operation type: "+w
|
|
2702
2638
|
return f.error(e),{content:[{type:"text",text:"\u274c **Request Operations Failed:** "+e}],isError:!0}}}}catch(e){return f.error("Request operations failed",{error:e instanceof Error?e.stack:e+""}),g.incrementCounter("request_operations_errors",1),{content:[{type:"text",text:"\u274c **Request Operations Failed:** "+(0,u.getErrorMessage)(e)}],isError:!0}}}
|
|
2703
2639
|
const r=t(6183),n=t(5715),o=t(6416),s=t(5434),i=t(8037),a=t(233),c=t(1537),l=t(4306),u=t(8824)},4710(e,exports,t){"use strict"
|
|
2704
2640
|
var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}}
|
|
@@ -2881,13 +2817,13 @@ exports.WorktreeGitAdapter=class{constructor(e,t,r,o,s){this.mainGit=e,this.work
|
|
|
2881
2817
|
try{const r=o.WorkspaceValidation.validateRequestId(e)
|
|
2882
2818
|
if(!r.isValid){const t="Invalid request ID: "+r.errors.join(", ")
|
|
2883
2819
|
throw o.WorkspaceLogging.logOperation(this.logger,"error",t,e,"multi-agent","setupWorkspace"),Error(t)}const n=r.sanitized,s="requests/"+n,i=await this.branchManager.getBaseBranch()
|
|
2884
|
-
o.WorkspaceLogging.logOperation(this.logger,"info","Setting up multi-agent workspace",e,"multi-agent","setupWorkspace",{branchName:s,mainBranch:i,architecture:"
|
|
2820
|
+
o.WorkspaceLogging.logOperation(this.logger,"info","Setting up multi-agent workspace",e,"multi-agent","setupWorkspace",{branchName:s,mainBranch:i,architecture:"standard"})
|
|
2885
2821
|
const a=await this.getWorktreeInfo(n)
|
|
2886
2822
|
if(!a){if(this.logger.info("No worktree found, checking for quick-edit branch in main repo",{requestId:n,branchName:s}),!(await this.mainGit.branch()).all.includes(s))throw Error(`No worktree or branch found for request ${e}. Use initializeRequest() first.`)
|
|
2887
2823
|
return this.logger.info("Found quick-edit branch in main repo, using main repo for operations",{requestId:n,branchName:s}),Date.now(),{mode:"multi-agent",requestId:n,branchName:s,workingDirectory:this.worktreeManager.mainRepoPath,isWorktree:!1,branchInfo:{mainBranch:i,currentBranch:s},worktreeInfo:void 0}}const c=Date.now()-t
|
|
2888
|
-
return o.WorkspaceLogging.logOperation(this.logger,"info","Worktree info retrieved successfully",e,"multi-agent","setupWorkspace",{worktreePath:a.worktreePath,branchName:a.branchName,duration:c,architecture:"
|
|
2824
|
+
return o.WorkspaceLogging.logOperation(this.logger,"info","Worktree info retrieved successfully",e,"multi-agent","setupWorkspace",{worktreePath:a.worktreePath,branchName:a.branchName,duration:c,architecture:"standard"}),this.currentRequestId=n,this.currentWorktreePath=a.worktreePath,{mode:"multi-agent",requestId:n,branchName:s,workingDirectory:a.worktreePath,isWorktree:!0,branchInfo:{mainBranch:i,currentBranch:s},worktreeInfo:{worktreePath:a.worktreePath,branchName:a.branchName}}}catch(r){const n=Date.now()-t
|
|
2889
2825
|
throw o.WorkspaceLogging.logOperation(this.logger,"error","Failed to set up multi-agent workspace",e,"multi-agent","setupWorkspace",{error:(0,i.getErrorMessage)(r),duration:n}),r}}async detectConflicts(e,t){const r=e.isWorktree&&e.worktreeInfo,n=r?e.worktreeInfo.worktreePath:e.workingDirectory
|
|
2890
|
-
return this.logger.info("Detecting conflicts in multi-agent mode",{requestId:e.requestId,sourceBranch:t.sourceBranch,targetBranch:t.targetBranch,workingPath:n,isWorktree:r,isQuickEdit:!r}),await this.conflictDetector.detectConflicts({mode:
|
|
2826
|
+
return this.logger.info("Detecting conflicts in multi-agent mode",{requestId:e.requestId,sourceBranch:t.sourceBranch,targetBranch:t.targetBranch,workingPath:n,isWorktree:r,isQuickEdit:!r}),await this.conflictDetector.detectConflicts({mode:"multi-agent",worktreePath:r?e.worktreeInfo.worktreePath:e.workingDirectory,logger:this.logger,requestId:t.requestId,sourceBranch:t.sourceBranch,targetBranch:t.targetBranch})}async stageAndCommitChanges(e){if(!e.worktreeInfo)throw Error("Worktree info not available in context")
|
|
2891
2827
|
this.logger.info("Staging and committing changes in multi-agent mode",{requestId:e.requestId,worktreePath:e.worktreeInfo.worktreePath})
|
|
2892
2828
|
const t=(0,r.simpleGit)(e.worktreeInfo.worktreePath)
|
|
2893
2829
|
try{const r=await t.status()
|
|
@@ -2932,7 +2868,7 @@ module.exports=require("winston")},5172(e,exports){"use strict"
|
|
|
2932
2868
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.setGlobalClientInfo=function(e,r,n){const o=process.env.ALCHEMY_SESSION_TAG||n||function(){const e=new Date
|
|
2933
2869
|
return`mcp-${(e.getHours()+"").padStart(2,"0")}${(e.getMinutes()+"").padStart(2,"0")}${(e.getSeconds()+"").padStart(2,"0")}-${Math.random().toString(36).substring(2,7)}`}()
|
|
2934
2870
|
t={name:e,version:r,sessionTag:o}},exports.setSessionTag=function(e){t.sessionTag=e},exports.getGlobalClientInfo=function(){return{clientName:t.name,clientVersion:t.version,sessionTag:t.sessionTag}}
|
|
2935
|
-
let t={name:"
|
|
2871
|
+
let t={name:"OpenCode",version:"1.0.0",sessionTag:"unknown-session"}},5187(e,exports,t){"use strict"
|
|
2936
2872
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.CLISessionClient=void 0
|
|
2937
2873
|
const r=t(7645),n=t(2161)
|
|
2938
2874
|
class o extends r.ConnectionAwareClient{constructor(e,t,r,n,o,s,i){const a=t.child({component:"cli-session-client"}),c=s||{isInOfflineMode(){return!1},isOffline(){return!1},setOfflineMode(){},async checkConnectivity(){return!0},getHealthCheckStats(){return{isOffline:!1,consecutiveFailures:0,currentBackoffMs:0,lastCheckTime:0}},cleanup(){}}
|
|
@@ -2964,42 +2900,7 @@ const r=await this.requestWithRetry("POST",`/api/projects/${t}/cli-sessions/batc
|
|
|
2964
2900
|
return(0,n.safeGetResponseData)(r,{},this.logger)}}exports.CLISessionClient=o},5216(e,exports,t){"use strict"
|
|
2965
2901
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.def=void 0
|
|
2966
2902
|
const r=t(6183),n=t(4041)
|
|
2967
|
-
exports.def={name:"switch_to_branch",description:'Switch between main branch and request feature branches.\n\nUSAGE:\n- Main branch: {} or {"branch": "main"}\n- Request branch: {"branch": "req123"}\n\nAll file operations use the active branch context. Usually only needed if we want to read files or do a search on a branch we are currently not working on.',schema:r.SwitchToBranchSchema,annotations:{title:"Switch to Branch",readOnlyHint:!1,destructiveHint:!1},handler(e,t){return(0,n.handleSwitchToBranch)(e,t.context,t.apiClient.getRequestClient(),t.logger,t.metrics)}}},
|
|
2968
|
-
var r,n=this&&this.__createBinding||(Object.create?function(e,t,r,n){void 0===n&&(n=r)
|
|
2969
|
-
var o=Object.getOwnPropertyDescriptor(t,r)
|
|
2970
|
-
o&&!("get"in o?!t.__esModule:o.writable||o.configurable)||(o={enumerable:!0,get(){return t[r]}}),Object.defineProperty(e,n,o)}:function(e,t,r,n){void 0===n&&(n=r),e[n]=t[r]}),o=this&&this.__setModuleDefault||(Object.create?function(e,t){Object.defineProperty(e,"default",{enumerable:!0,value:t})}:function(e,t){e.default=t}),s=this&&this.__importStar||(r=function(e){return r=Object.getOwnPropertyNames||function(e){var t=[]
|
|
2971
|
-
for(var r in e)({}).hasOwnProperty.call(e,r)&&(t[t.length]=r)
|
|
2972
|
-
return t},r(e)},function(e){if(e&&e.__esModule)return e
|
|
2973
|
-
var t={}
|
|
2974
|
-
if(null!=e)for(var s=r(e),i=0;i<s.length;i++)"default"!==s[i]&&n(t,e,s[i])
|
|
2975
|
-
return o(t,e),t})
|
|
2976
|
-
Object.defineProperty(exports,"__esModule",{value:!0}),exports.MultiAgentConfigManager=void 0,exports.parseSingleFlag=function(e){for(let t=0;t<e.length;t++)if("--single"===e[t])return!0},exports.isMultiAgentModeEnabled=function(e,t){const r=e||process.cwd(),n=c.join(r,l.ALCHEMY_DIR_NAME),o=c.join(n,"config.json")
|
|
2977
|
-
t?.debug("isMultiAgentModeEnabled called",{baseDir:e,configPath:o})
|
|
2978
|
-
try{if(a.existsSync(n)||(t?.debug(".alchemy_lab directory does not exist, creating it"),a.mkdirSync(n,{recursive:!0})),a.existsSync(o)){t?.debug("Config file exists, reading")
|
|
2979
|
-
const e=a.readFileSync(o,"utf-8"),r=JSON.parse(e),n=!1!==r.multiAgent
|
|
2980
|
-
return t?.debug("Parsed config",{multiAgent:n,config:r}),n}{t?.debug("Config file does not exist, creating with defaults")
|
|
2981
|
-
const e={multiAgent:!0,lockTimeout:3600,worktreeCleanupDelay:900,maxWorktreeAge:24,cleanupInterval:15,preserveBranchesOnCleanup:!0,maxConcurrentSessions:10,sessionTimeoutWarning:45}
|
|
2982
|
-
return a.writeFileSync(o,JSON.stringify(e,null,2),"utf-8"),t?.debug("Created default config",{multiAgent:!0}),!0}}catch(e){return t?.debug("Error reading multi-agent config, defaulting to multi-agent mode",{error:(0,u.getErrorMessage)(e)}),!0}},exports.getLockTimeoutFromEnv=function(){const e=process.env.ALCHEMY_LOCK_TIMEOUT
|
|
2983
|
-
return e&&!isNaN(parseInt(e))?1e3*parseInt(e):36e5}
|
|
2984
|
-
const i=s(t(1943)),a=s(t(9896)),c=s(t(6928)),l=t(4139),u=t(8824)
|
|
2985
|
-
exports.MultiAgentConfigManager=class{constructor(e,t){this.baseDir=e,this.logger=t.child({component:"multi-agent-config"}),this.config=this.getDefaultConfig()}async initialize(){try{const e=this.loadEnvironmentConfig(),t=await this.loadConfigFile()
|
|
2986
|
-
return this.config=this.mergeConfigs(this.getDefaultConfig(),t,e),this.logger.info("Multi-agent configuration loaded",{enabled:this.config.enabled,source:this.getConfigSource(),lockTimeout:this.config.lockTimeout,worktreeCleanupDelay:this.config.worktreeCleanupDelay}),this.config}catch(e){return this.logger.error("Failed to load multi-agent configuration",{error:(0,u.getErrorMessage)(e)}),this.config=this.getDefaultConfig(),this.config}}getConfig(){return{...this.config}}isMultiAgentEnabled(){return this.config.enabled}getDefaultConfig(){return{enabled:!1,lockTimeout:36e5,worktreeCleanupDelay:9e5,maxWorktreeAge:864e5,cleanupInterval:9e5,preserveBranchesOnCleanup:!0,maxConcurrentSessions:10,sessionTimeoutWarning:27e5}}loadEnvironmentConfig(){const e={},t=process.env.ALCHEMY_MULTI_AGENT
|
|
2987
|
-
void 0!==t&&(e.enabled="true"===t.toLowerCase())
|
|
2988
|
-
const r=process.env.ALCHEMY_LOCK_TIMEOUT
|
|
2989
|
-
r&&!isNaN(parseInt(r))&&(e.lockTimeout=1e3*parseInt(r))
|
|
2990
|
-
const n=process.env.ALCHEMY_WORKTREE_CLEANUP_DELAY
|
|
2991
|
-
n&&!isNaN(parseInt(n))&&(e.worktreeCleanupDelay=1e3*parseInt(n))
|
|
2992
|
-
const o=process.env.ALCHEMY_MAX_WORKTREE_AGE
|
|
2993
|
-
o&&!isNaN(parseInt(o))&&(e.maxWorktreeAge=36e5*parseInt(o))
|
|
2994
|
-
const s=process.env.ALCHEMY_PRESERVE_BRANCHES
|
|
2995
|
-
void 0!==s&&(e.preserveBranchesOnCleanup="true"===s.toLowerCase())
|
|
2996
|
-
const i=process.env.ALCHEMY_MAX_CONCURRENT_SESSIONS
|
|
2997
|
-
return i&&!isNaN(parseInt(i))&&(e.maxConcurrentSessions=parseInt(i)),e}async loadConfigFile(){const e=[c.join(this.baseDir,"alchemy.config.json"),c.join(this.baseDir,".alchemyrc.json"),c.join(this.baseDir,l.ALCHEMY_DIR_NAME,"config.json")]
|
|
2998
|
-
for(const t of e)try{const e=await i.readFile(t,"utf-8"),r=JSON.parse(e)
|
|
2999
|
-
return this.logger.debug("Loaded configuration from file",{configPath:t,config:r}),this.convertFileConfigToRuntime(r)}catch(e){this.logger.debug("Config file not found or invalid",{configPath:t,error:(0,u.getErrorMessage)(e)})}return this.logger.debug("No configuration file found",{searchPaths:e}),{}}convertFileConfigToRuntime(e){const t={}
|
|
3000
|
-
return void 0!==e.multiAgent&&(t.enabled=e.multiAgent),void 0!==e.lockTimeout&&(t.lockTimeout=1e3*e.lockTimeout),void 0!==e.worktreeCleanupDelay&&(t.worktreeCleanupDelay=1e3*e.worktreeCleanupDelay),void 0!==e.maxWorktreeAge&&(t.maxWorktreeAge=36e5*e.maxWorktreeAge),void 0!==e.cleanupInterval&&(t.cleanupInterval=6e4*e.cleanupInterval),void 0!==e.preserveBranchesOnCleanup&&(t.preserveBranchesOnCleanup=e.preserveBranchesOnCleanup),void 0!==e.maxConcurrentSessions&&(t.maxConcurrentSessions=e.maxConcurrentSessions),void 0!==e.sessionTimeoutWarning&&(t.sessionTimeoutWarning=6e4*e.sessionTimeoutWarning),t}mergeConfigs(e,t,r){return{...e,...t,...r}}getConfigSource(){const e=[]
|
|
3001
|
-
return void 0!==process.env.ALCHEMY_MULTI_AGENT&&e.push("environment"),e.push("defaults"),e.join(", ")}async createSampleConfig(e){const t=e||c.join(this.baseDir,"alchemy.config.json.sample"),r=JSON.stringify({multiAgent:!1,lockTimeout:3600,worktreeCleanupDelay:900,maxWorktreeAge:24,cleanupInterval:15,preserveBranchesOnCleanup:!0,maxConcurrentSessions:10,sessionTimeoutWarning:45},null,2)
|
|
3002
|
-
return await i.writeFile(t,r),this.logger.info("Created sample configuration file",{configPath:t}),t}validateConfig(e){6e4>e.lockTimeout&&this.logger.warn("Lock timeout is very short",{lockTimeout:e.lockTimeout,recommended:">=60000 (1 minute)"}),3e4>e.worktreeCleanupDelay&&this.logger.warn("Worktree cleanup delay is very short",{cleanupDelay:e.worktreeCleanupDelay,recommended:">=300000 (5 minutes)"}),e.maxConcurrentSessions>50&&this.logger.warn("Max concurrent sessions is very high",{maxSessions:e.maxConcurrentSessions,recommended:"<=20"})}}},5247(e,exports,t){"use strict"
|
|
2903
|
+
exports.def={name:"switch_to_branch",description:'Switch between main branch and request feature branches.\n\nUSAGE:\n- Main branch: {} or {"branch": "main"}\n- Request branch: {"branch": "req123"}\n\nAll file operations use the active branch context. Usually only needed if we want to read files or do a search on a branch we are currently not working on.',schema:r.SwitchToBranchSchema,annotations:{title:"Switch to Branch",readOnlyHint:!1,destructiveHint:!1},handler(e,t){return(0,n.handleSwitchToBranch)(e,t.context,t.apiClient.getRequestClient(),t.logger,t.metrics)}}},5247(e,exports,t){"use strict"
|
|
3003
2904
|
var r,n=this&&this.__createBinding||(Object.create?function(e,t,r,n){void 0===n&&(n=r)
|
|
3004
2905
|
var o=Object.getOwnPropertyDescriptor(t,r)
|
|
3005
2906
|
o&&!("get"in o?!t.__esModule:o.writable||o.configurable)||(o={enumerable:!0,get(){return t[r]}}),Object.defineProperty(e,n,o)}:function(e,t,r,n){void 0===n&&(n=r),e[n]=t[r]}),o=this&&this.__setModuleDefault||(Object.create?function(e,t){Object.defineProperty(e,"default",{enumerable:!0,value:t})}:function(e,t){e.default=t}),s=this&&this.__importStar||(r=function(e){return r=Object.getOwnPropertyNames||function(e){var t=[]
|
|
@@ -3149,35 +3050,7 @@ const e=u.annotationId,t=u.body,n=r.getDocumentClient(),s=await n.replyToAnnotat
|
|
|
3149
3050
|
return o.incrementCounter("document_operations_total",1,{operation:"reply-to-annotation",success:!0}),{content:[{type:"text",text:`\u2705 **Reply Added**\n\n**Reply ID:** ${s.id}\n**Annotation:** ${e}\n**Body:** `+t}]}}case"resolve-annotation":{h.info("Resolving annotation")
|
|
3150
3051
|
const e=u.annotationId,t=r.getDocumentClient()
|
|
3151
3052
|
return await t.resolveAnnotation(p,e,d?"agent":void 0),o.incrementCounter("document_operations_total",1,{operation:"resolve-annotation",success:!0}),{content:[{type:"text",text:`\u2705 **Annotation Resolved**\n\n**Annotation:** ${e}\n**Status:** resolved`}]}}default:throw Error("Unknown operation type: "+g)}}catch(e){return h.error("document_operations failed",{error:e instanceof Error?e.stack:e+""}),o.incrementCounter("document_operations_errors",1),{content:[{type:"text",text:"\u274c **Document Operations Failed:** "+(0,u.getErrorMessage)(e)}],isError:!0}}}
|
|
3152
|
-
const i=t(6183),a=s(t(5967)),c=t(1572),l=t(1483),u=t(8824)},
|
|
3153
|
-
function r(e){const[t,...r]=e.split("/")
|
|
3154
|
-
return{provider:t||"anthropic",modelId:r.join("/")||e}}function n(e){const t={anthropic:!1,openai:!1}
|
|
3155
|
-
try{const n=(0,a.join)(e,"opencode.json")
|
|
3156
|
-
if((0,i.existsSync)(n)){const e=JSON.parse((0,i.readFileSync)(n,"utf8"))
|
|
3157
|
-
if(e.provider&&((e.provider.anthropic?.options?.apiKey||process.env.ANTHROPIC_API_KEY)&&(t.anthropic=!0),(e.provider.openai?.options?.apiKey||process.env.OPENAI_API_KEY)&&(t.openai=!0)),e.model){const{provider:n}=r(e.model)
|
|
3158
|
-
t[n]=!0}}process.env.ANTHROPIC_API_KEY&&(t.anthropic=!0),process.env.OPENAI_API_KEY&&(t.openai=!0)}catch(e){t.anthropic=!0}return t}function o(e){try{const t=(0,a.join)(e,"opencode.json")
|
|
3159
|
-
if((0,i.existsSync)(t))return JSON.parse((0,i.readFileSync)(t,"utf8")).model||null}catch(e){}return null}function s(e,t,n,o){const s=r(e)
|
|
3160
|
-
let i=s.provider
|
|
3161
|
-
if("inherit"!==t){if(!o[t])return{provider:s.provider,modelId:s.modelId,fullModel:e,resolved:!1,reason:`Preferred provider '${t}' not available, using main session model`}
|
|
3162
|
-
i=t}const a=function(e,t){const r=c[e]
|
|
3163
|
-
if(!r)return null
|
|
3164
|
-
const n=[...r].sort(((e,t)=>t.length-e.length))
|
|
3165
|
-
for(const e of n)if(t.includes(e))return e
|
|
3166
|
-
return null}(s.provider,s.modelId),l=c[s.provider],u=c[i]
|
|
3167
|
-
if(!a||!l||!u)return{provider:s.provider,modelId:s.modelId,fullModel:e,resolved:!1,reason:`Could not determine model family for '${s.modelId}', using main session model`}
|
|
3168
|
-
const d=l.indexOf(a)
|
|
3169
|
-
let h,g=0
|
|
3170
|
-
if("one_down"===n&&(g=1),"two_down"===n&&(g=2),i===s.provider)h=d+g
|
|
3171
|
-
else{const e=l.length>1?d/(l.length-1):0
|
|
3172
|
-
h=Math.round(e*(u.length-1))+g}h=Math.min(h,u.length-1),h=Math.max(h,0)
|
|
3173
|
-
const p=u[h]
|
|
3174
|
-
let f
|
|
3175
|
-
var m,y
|
|
3176
|
-
return i===s.provider?(m=a,y=p,f=s.modelId.replace(m,y)):f=p,{provider:i,modelId:f,fullModel:`${i}/${f}`,resolved:!0}}Object.defineProperty(exports,"__esModule",{value:!0}),exports.parseModelString=r,exports.getAvailableProviders=n,exports.getMainSessionModel=o,exports.resolveModelTier=s,exports.resolveAgentModel=function(e,t="inherit",i="same"){const a=o(e)
|
|
3177
|
-
if(!a)return{provider:"anthropic",modelId:"claude-sonnet-4-5",fullModel:"anthropic/claude-sonnet-4-5",resolved:!1,reason:"Could not determine main session model, using default"}
|
|
3178
|
-
if("inherit"===t&&"same"===i){const e=r(a)
|
|
3179
|
-
return{provider:e.provider,modelId:e.modelId,fullModel:a,resolved:!0}}return s(a,t,i,n(e))}
|
|
3180
|
-
const i=t(9896),a=t(6928),c={anthropic:["opus","sonnet","haiku"]}},5674(e,exports,t){"use strict"
|
|
3053
|
+
const i=t(6183),a=s(t(5967)),c=t(1572),l=t(1483),u=t(8824)},5674(e,exports,t){"use strict"
|
|
3181
3054
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.ConnectionError=void 0
|
|
3182
3055
|
const r=t(441)
|
|
3183
3056
|
class n extends Error{constructor(e,t,o,s={}){super(e),this.statusCode=503,this.retryable=!0,this.metadata={},this.name="ConnectionError",this.code=r.CONNECTION_ERROR,this.operation=t,this.lastConnectionAttempt=o,this.details={...s,operation:t,lastConnectionAttempt:o},Object.setPrototypeOf(this,n.prototype)}static operationRequiresConnectivity(e,t="",r){const o=`Cannot perform ${e}${t?` (${t})`:""} - not connected to remote server. Please check your network connection and try again. If the problem persists, verify that the remote server is running and accessible.`,s={operationType:e,operationDetails:t,timestamp:(new Date).toISOString(),suggestions:["Check your internet connection","Verify the remote server URL is correct","Ensure the remote server is running","Check for any firewall or proxy settings that might be blocking the connection"]}
|
|
@@ -3251,50 +3124,50 @@ else{if(!E)throw Error("Either paths or operations must be specified")
|
|
|
3251
3124
|
S=E.map((e=>{if(e.path)return{type:"file",target:e.path}
|
|
3252
3125
|
if(e.documentId)return{type:"document",target:e.documentId}
|
|
3253
3126
|
throw Error("Invalid operation: neither path nor documentId specified")}))}if(0===S.length)throw Error("At least one file or document must be specified for deletion")
|
|
3254
|
-
const T=S.filter((e=>"file"===e.type)),
|
|
3255
|
-
i.info("Starting mixed file and document deletion operation",{taskId:C,totalOperations:S.length,fileOperations:T.length,documentOperations:
|
|
3256
|
-
const
|
|
3257
|
-
i.info("Initial branch context",{initialBranch:
|
|
3127
|
+
const T=S.filter((e=>"file"===e.type)),R=S.filter((e=>"document"===e.type)),P=S.length
|
|
3128
|
+
i.info("Starting mixed file and document deletion operation",{taskId:C,totalOperations:S.length,fileOperations:T.length,documentOperations:R.length,comment:q}),l.validateTaskIdFormat(C,i,o,b.metricsPrefix)
|
|
3129
|
+
const M=t.getCurrentBranchContext?await t.getCurrentBranchContext():{branch:null,requestId:null,isMain:!0}
|
|
3130
|
+
i.info("Initial branch context",{initialBranch:M.branch,initialRequestId:M.requestId,isMain:M.isMain})
|
|
3258
3131
|
const x=[]
|
|
3259
3132
|
for(const e of T){const{normalizedPath:r,fullPath:n}=l.validateAndNormalizePath(e.target,t)
|
|
3260
3133
|
x.push({normalized:r,full:n})}k=l.FileOperationPhase.TASK_VALIDATION,o.incrementCounter("delete_files_phase",1,{phase:k})
|
|
3261
|
-
const
|
|
3262
|
-
A.taskPromoted&&i.info(`Auto-promoted task ${C} (${
|
|
3134
|
+
const j=x.length>0?x[0].normalized:"document_operations",O=await l.validateTaskId(C,j,n,i,o,b.metricsPrefix),$=O?.requestId,D=await l.validateWorkItemStates(C,j,n,I,t,i,o,b.metricsPrefix),A=await l.autoPromoteTaskStatus(C,O.status,$,D.request?.status,j,n,I,i,o,b.metricsPrefix)
|
|
3135
|
+
A.taskPromoted&&i.info(`Auto-promoted task ${C} (${O.title||"Untitled"}) to in_progress for mixed operations`,{taskId:C,taskTitle:O.title,previousStatus:O.status,newStatus:A.newTaskStatus,totalOperations:S.length,fileOperations:T.length,documentOperations:R.length}),A.requestPromoted&&i.info(`Auto-promoted request ${$} to in_progress for file operations`,{requestId:$,previousStatus:D.request?.status,newStatus:A.newRequestStatus,triggeringTaskId:C})
|
|
3263
3136
|
const F=await l.ensureCorrectWorkspaceContext({taskPromoted:A.taskPromoted,requestId:$,context:t,operation:"delete-files",logger:i,metrics:o,metricsPrefix:b.metricsPrefix})
|
|
3264
3137
|
if(!F.success){if(F.isLockConflict)return{content:[{type:"text",text:"\u274c "+F.error}],isError:!0}
|
|
3265
3138
|
throw Error(F.error)}let N={hadUserMods:!1,userModsCommitHash:void 0}
|
|
3266
3139
|
if(t.git)try{i.debug("[DELETE-FILES] Checking for user changes before mixed delete operations")
|
|
3267
3140
|
const e=await(0,h.commitUserChangesBeforeToolOperation)(t.git,"delete-files",{requestId:$,taskId:C,workspaceManager:t.workspaceManager},i,o)
|
|
3268
|
-
e.userChangesCommitted&&(i.debug("[DELETE-FILES] User changes committed before mixed delete operations",{commitHash:e.commitHash?.substring(0,8),filesCommitted:e.filesCommitted}),i.info("User changes committed before mixed delete-files operation",{taskId:C,totalOperations:S.length,fileOperations:T.length,documentOperations:
|
|
3269
|
-
const{toolRecordId:L,localToolRecordId:z}=await l.createFileOperationRecords(C,$,t.projectId,b.recordType,
|
|
3141
|
+
e.userChangesCommitted&&(i.debug("[DELETE-FILES] User changes committed before mixed delete operations",{commitHash:e.commitHash?.substring(0,8),filesCommitted:e.filesCommitted}),i.info("User changes committed before mixed delete-files operation",{taskId:C,totalOperations:S.length,fileOperations:T.length,documentOperations:R.length,userCommitHash:e.commitHash?.substring(0,8),userFilesCommitted:e.filesCommitted}),N={hadUserMods:!0,userModsCommitHash:e.commitHash})}catch(e){i.debug("[DELETE-FILES] Pre-tool commit failed, continuing with mixed delete operations",{error:e instanceof Error?e.message:e+""}),i.warn("Pre-tool user changes commit failed, continuing with mixed delete operation",{taskId:C,totalOperations:S.length,fileOperations:T.length,documentOperations:R.length,error:e instanceof Error?e.message:e+""})}i.debug("[DELETE-FILES] Proceeding with mixed delete operations",{totalOperations:S.length,fileDeletes:T.length,documentDeletes:R.length}),k=l.FileOperationPhase.RECORD_CREATION,o.incrementCounter("delete_files_phase",1,{phase:k})
|
|
3142
|
+
const{toolRecordId:L,localToolRecordId:z}=await l.createFileOperationRecords(C,$,t.projectId,b.recordType,j,{totalOperations:S.length,fileOperations:T.length,documentOperations:R.length,filePaths:x.map((e=>e.normalized)),documentIds:R.map((e=>e.target)),userComment:q,hadUserMods:N.hadUserMods,userModsCommitHash:N.userModsCommitHash},n,d,i,o,b.metricsPrefix,s)
|
|
3270
3143
|
y=L,w=L,k=b.fileOperationPhase,o.incrementCounter("delete_files_phase",1,{phase:k})
|
|
3271
3144
|
const B=[]
|
|
3272
3145
|
let H=0
|
|
3273
|
-
|
|
3146
|
+
R.length>0&&r.setProjectId(t.projectId)
|
|
3274
3147
|
for(let e=0;e<x.length;e++){const t=x[e],r={type:"file",path:t.normalized,success:!1,replacements:[],successfulReplacements:0,failedReplacements:0}
|
|
3275
3148
|
try{try{await a.default.access(t.full)}catch(e){throw Error("File not found: "+t.normalized)}if((await a.default.stat(t.full)).isDirectory())throw Error("Cannot 'delete' a directory: "+t.normalized)
|
|
3276
|
-
await a.default.unlink(t.full),r.success=!0,H++,i.info("Successfully deleted file",{path:t.normalized})}catch(e){r.error=(0,f.getErrorMessage)(e),i.warn("Failed to delete file "+t.normalized,{error:r.error})}B.push(r)}const U=
|
|
3277
|
-
for(const e of
|
|
3149
|
+
await a.default.unlink(t.full),r.success=!0,H++,i.info("Successfully deleted file",{path:t.normalized})}catch(e){r.error=(0,f.getErrorMessage)(e),i.warn("Failed to delete file "+t.normalized,{error:r.error})}B.push(r)}const U=R.length>0?r.getDocumentClient():null
|
|
3150
|
+
for(const e of R){const t=e.target,n={type:"document",documentId:t,success:!1,replacements:[],successfulReplacements:0,failedReplacements:0}
|
|
3278
3151
|
try{let e
|
|
3279
3152
|
try{if(e=await U.getDocument(t),n.filename=e.filename,i.info("Document found for archival",{documentId:e.id,filename:e.filename,type:e.type,requestId:e.requestId}),e.requestId)try{await(0,g.validateRequestStatusForDocumentOperation)(e.requestId,I,i,o,"delete-document")}catch(e){if(e instanceof u.ValidationError)throw Error(e.message)
|
|
3280
3153
|
throw e}try{await(0,p.ensureDocumentNotLocked)(t,r,i,o,"delete-document-archive")}catch(e){if(e instanceof u.ValidationError)throw Error(e.message)
|
|
3281
3154
|
throw e}}catch(e){throw Error(`Document not found or validation failed: ${t}. ${(0,f.getErrorMessage)(e)}`)}const s=await U.archiveDocument(t)
|
|
3282
|
-
n.success=!0,n.filename=s.filename,H++,i.info("Document archived successfully",{documentId:s.id,filename:s.filename,archivedAt:s.archived_at})}catch(e){n.error=(0,f.getErrorMessage)(e),i.warn("Failed to delete document "+t,{error:n.error})}B.push(n)}const
|
|
3283
|
-
o.recordValue("delete_files_time",
|
|
3284
|
-
let
|
|
3155
|
+
n.success=!0,n.filename=s.filename,H++,i.info("Document archived successfully",{documentId:s.id,filename:s.filename,archivedAt:s.archived_at})}catch(e){n.error=(0,f.getErrorMessage)(e),i.warn("Failed to delete document "+t,{error:n.error})}B.push(n)}const G=Date.now()-m
|
|
3156
|
+
o.recordValue("delete_files_time",G),o.incrementCounter("delete_files_operations_total",P),o.incrementCounter("delete_files_operations_success",H),o.incrementCounter("delete_files_operations_failed",P-H),o.incrementCounter("delete_files_file_operations",T.length),o.incrementCounter("delete_files_document_operations",R.length),H===P?o.incrementCounter("delete_files_success",1):H>0?o.incrementCounter("delete_files_partial_success",1):o.incrementCounter("delete_files_total_failure",1)
|
|
3157
|
+
let W=null
|
|
3285
3158
|
if(H>0){k=l.FileOperationPhase.GIT_COMMIT,o.incrementCounter("delete_files_phase",1,{phase:k})
|
|
3286
3159
|
const e=B.filter((e=>e.success)),r=e.filter((e=>"file"===e.type)).length,n=e.filter((e=>"document"===e.type)).length
|
|
3287
3160
|
let s
|
|
3288
|
-
s=r>0&&n>0?`Delete ${r} files and ${n} documents - ${q}`:r>0?1===r?"Delete file - "+q:`Delete ${r} files - ${q}`:1===n?"Delete document - "+q:`Delete ${n} documents - ${q}`,
|
|
3161
|
+
s=r>0&&n>0?`Delete ${r} files and ${n} documents - ${q}`:r>0?1===r?"Delete file - "+q:`Delete ${r} files - ${q}`:1===n?"Delete document - "+q:`Delete ${n} documents - ${q}`,W=await l.commitToGit(C,j,L,z,s,t,i,o,b.metricsPrefix)}k=l.FileOperationPhase.RECORD_UPDATE_SUCCESS,o.incrementCounter("delete_files_phase",1,{phase:k})
|
|
3289
3162
|
const V=B.filter((e=>e.success)),J=B.filter((e=>!e.success))
|
|
3290
|
-
await l.updateFileOperationRecords(C,y,w,
|
|
3163
|
+
await l.updateFileOperationRecords(C,y,w,j,b.recordType,H===P?`Successfully deleted all ${P} operations`:`Deleted ${H}/${P} operations successfully`,{status:H===P?"completed":"partial_success",commitHash:W?.commitHash,previousCommitHash:W?.previousCommitHash,totalOperations:P,fileOperations:T.length,documentOperations:R.length,successCount:H,failureCount:P-H,successfulOperations:V.map((e=>({type:e.type,path:e.path,documentId:e.documentId,filename:e.filename}))),failedOperations:J.map((e=>({type:e.type,path:e.path,documentId:e.documentId,filename:e.filename,error:e.error}))),userComment:q,hadUserMods:N.hadUserMods,userModsCommitHash:N.userModsCommitHash},H===P?`Successfully deleted all ${P} operations`:`Deleted ${H}/${P} operations successfully`,n,d,i,o,b.metricsPrefix)
|
|
3291
3164
|
const K=t.getCurrentBranchContext?await t.getCurrentBranchContext():{branch:null,requestId:null,isMain:!0}
|
|
3292
3165
|
let Y=""
|
|
3293
|
-
if(H===
|
|
3294
|
-
Y=e>0&&t>0?`Successfully deleted ${e} files and ${t} documents`:e>0?`Successfully deleted all ${e} ${1===e?"file":"files"}`:`Successfully archived all ${t} ${1===t?"document":"documents"}`}else Y=H>0?`Successfully deleted ${H}/${
|
|
3166
|
+
if(H===P){const e=V.filter((e=>"file"===e.type)).length,t=V.filter((e=>"document"===e.type)).length
|
|
3167
|
+
Y=e>0&&t>0?`Successfully deleted ${e} files and ${t} documents`:e>0?`Successfully deleted all ${e} ${1===e?"file":"files"}`:`Successfully archived all ${t} ${1===t?"document":"documents"}`}else Y=H>0?`Successfully deleted ${H}/${P} operations.\n\nFailed operations:\n`+B.filter((e=>!e.success)).map((e=>{const t="file"===e.type?e.path:`${e.filename||e.documentId} (${e.documentId})`
|
|
3295
3168
|
return`\u2022 ${e.type}: ${t}: ${e.error}`})).join("\n"):"All delete operations failed:\n"+B.map((e=>{const t="file"===e.type?e.path:`${e.filename||e.documentId} (${e.documentId})`
|
|
3296
3169
|
return`\u2022 ${e.type}: ${t}: ${e.error}`})).join("\n")
|
|
3297
|
-
return
|
|
3170
|
+
return W?.commitHash&&(Y+="\nCommit: "+W.commitHash.substring(0,8)),K.requestId&&(Y+="\nBranch: "+K.requestId),F.lockAcquired&&F.lockedRequestId&&(Y+="\n\u{1f512} **Locked request:** "+F.lockedRequestId),{content:[{type:"text",text:Y}],isError:0===H}}catch(n){if(e.taskId&&r)try{const o=r.getToolRecordClient(),s=n instanceof u.NotFoundError||n instanceof u.ValidationError||n instanceof d.ZodError
|
|
3298
3171
|
await o.createToolRecord({...s?{}:{taskId:e.taskId},projectId:t.projectId,type:"delete-files",metadata:{status:"failed",timestamp:(new Date).toISOString(),totalOperations:e.operations?.length||e.paths?.length||0,fileOperations:e.paths?.length||e.operations?.filter((e=>e.path))?.length||0,documentOperations:e.operations?.filter((e=>e.documentId))?.length||0,paths:e.paths||e.operations?.filter((e=>e.path))?.map((e=>e.path))||[],documentIds:e.operations?.filter((e=>e.documentId))?.map((e=>e.documentId))||[],userComment:e.comment,error:(0,f.getErrorMessage)(n),errorDetails:n instanceof Error?n.stack:n+"",phase:k,attemptedTaskId:e.taskId,taskIdValidationFailed:s},note:"Failed to delete files - "+(0,f.getErrorMessage)(n)})}catch(t){i.error("Failed to create failure record for delete-files operation",{error:t instanceof Error?t.message:t+"",taskId:e.taskId,totalOperations:e.operations?.length||e.paths?.length||0,fileOperations:e.paths?.length||e.operations?.filter((e=>e.path))?.length||0,documentOperations:e.operations?.filter((e=>e.documentId))?.length||0})}const s=Date.now()-m
|
|
3299
3172
|
if(o.recordValue("delete_files_time",s),o.incrementCounter("delete_files_errors",1),i.error("Error in delete-files operation:",{error:(0,f.getErrorMessage)(n),time:s}),(y||w)&&e.taskId){k=l.FileOperationPhase.RECORD_UPDATE_FAILURE
|
|
3300
3173
|
try{const t=r.getTaskClient(),s=r.getToolRecordClient()
|
|
@@ -3308,7 +3181,7 @@ return t},r(e)},function(e){if(e&&e.__esModule)return e
|
|
|
3308
3181
|
var t={}
|
|
3309
3182
|
if(null!=e)for(var s=r(e),i=0;i<s.length;i++)"default"!==s[i]&&n(t,e,s[i])
|
|
3310
3183
|
return o(t,e),t})
|
|
3311
|
-
Object.defineProperty(exports,"__esModule",{value:!0}),exports.DebugMultiAgentTool=void 0,exports.handleDebugMultiAgentStatus=async function(e,r,n){try{const e={environmentVariables:{
|
|
3184
|
+
Object.defineProperty(exports,"__esModule",{value:!0}),exports.DebugMultiAgentTool=void 0,exports.handleDebugMultiAgentStatus=async function(e,r,n){try{const e={environmentVariables:{MULTI_AGENT_MODE:"always enabled",ALCHEMY_LOCK_TIMEOUT:process.env.ALCHEMY_LOCK_TIMEOUT},workspaceManager:{available:!!r.workspaceManager,currentContext:r.workspaceManager?.getCurrentContext()||null,activeWorkspaces:r.workspaceManager?.listActiveWorkspaces()||[]},basePath:r.basePath,alchemyPath:a.join(r.basePath,c.ALCHEMY_DIR_NAME),multiAgentMode:!0,fileSystemChecks:{}},n=a.join(r.basePath,c.ALCHEMY_DIR_NAME),o=a.join(n,"worktrees")
|
|
3312
3185
|
if(e.fileSystemChecks={alchemyLabExists:i.existsSync(n),worktreeBaseExists:i.existsSync(o),worktreeContents:[]},e.fileSystemChecks.worktreeBaseExists)try{const t=i.readdirSync(o)
|
|
3313
3186
|
e.fileSystemChecks.worktreeContents=t}catch(t){e.fileSystemChecks.worktreeReadError=(0,l.getErrorMessage)(t)}try{const t=r.workspaceManager.listActiveWorkspaces()
|
|
3314
3187
|
e.activeWorkspaces=t}catch(t){e.workspaceManagerError=(0,l.getErrorMessage)(t)}try{const n=t(3807)(r.basePath),o=await n.status()
|
|
@@ -3361,22 +3234,22 @@ const n=await this.requestWithRetry("POST","/api/files/recover",t)
|
|
|
3361
3234
|
if(!(0,i.safeGetResponseData)(n,null))throw new r.ServiceError("Empty response when recovering file")
|
|
3362
3235
|
const o=(0,i.safeGetResponseData)(n,{success:!0,path:e.path,commitHash:e.commitHash,backupPath:void 0})
|
|
3363
3236
|
return this.logger.info("Successfully recovered file "+e.path,{path:o.path,commitHash:o.commitHash,backupPath:o.backupPath}),o}catch(t){throw this.logger.error("Failed to recover file "+e.path,{path:e.path,commitHash:e.commitHash,error:t instanceof Error?t.stack:t+""}),t}}}exports.FileOperationsClient=a},6183(e,exports,t){"use strict"
|
|
3364
|
-
Object.defineProperty(exports,"__esModule",{value:!0}),exports.PlanWriteSchema=exports.PlanReadSchema=exports.DocumentOperationsSchema=exports.SearchDocumentsSchema=exports.CreateDocumentSchema=exports.ReplaceLinesSchema=exports.InsertLinesSchema=exports.SwitchToRequestBranchSchema=exports.PlannerOpsSchema=exports.SpecialistOpsSchema=exports.SubagentOperationsSchema=exports.TaskOperationsSchema=exports.CompleteTaskSchema=exports.GetTaskInformationSchema=exports.GetRequestInformationSchema=exports.ListRequestsSchema=exports.ListTasksSchema=exports.SearchSchema=exports.QueryHistorySchema=exports.FileRecoverSchema=exports.FileHistorySchema=exports.DeleteFilesSchema=exports.DeleteFileSchema=exports.
|
|
3237
|
+
Object.defineProperty(exports,"__esModule",{value:!0}),exports.SwitchToMainBranchSchema=exports.PlanWriteSchema=exports.PlanReadSchema=exports.DocumentOperationsSchema=exports.SearchDocumentsSchema=exports.CreateDocumentSchema=exports.ReplaceLinesSchema=exports.InsertLinesSchema=exports.SwitchToRequestBranchSchema=exports.PlannerOpsSchema=exports.SpecialistOpsSchema=exports.SubagentOperationsSchema=exports.TaskOperationsSchema=exports.CompleteTaskSchema=exports.GetTaskInformationSchema=exports.GetRequestInformationSchema=exports.ListRequestsSchema=exports.ListTasksSchema=exports.SearchSchema=exports.QueryHistorySchema=exports.FileRecoverSchema=exports.FileHistorySchema=exports.DeleteFilesSchema=exports.DeleteFileSchema=exports.ReplaceInFilesSchema=exports.ReplaceStringsSchema=exports.ReplaceStringSchema=exports.MoveFilesSchema=exports.CreateDirectorySchema=exports.GetFileInfoSchema=exports.ListDirectorySchema=exports.ReadFilesSchema=exports.ViewAssetSchema=exports.WriteFileSchema=exports.UpdateTaskStatusSchema=exports.CreateTaskSchema=exports.CreateRequestSchema=exports.CompleteRequestSchema=exports.ExecutedTestSchema=exports.TestVerificationSchema=exports.TestDefinitionSchema=exports.AcceptanceCriterionSchema=exports.RecordTypeEnum=exports.EvidenceTypeEnum=exports.CriterionStatusEnum=exports.RequestStatusEnum=exports.TaskStatusEnum=exports.RequestTypeEnum=exports.TestCoverageTypeEnum=exports.CompletionStatusEnum=void 0,exports.UpdateSpecializationSchema=exports.SessionMessageOperationsSchema=exports.ReportTestResultsSchema=exports.ExecuteTestCommandSchema=exports.TestingReferenceSchema=exports.TestingProcessUpdateSchema=exports.TestingProcessCreateSchema=exports.TestingProcessGetSchema=exports.TestingProcessListSchema=exports.MetaReferenceSchema=exports.MetaAgentListSchema=exports.MetaWorkflowRemoveRecipeSchema=exports.MetaWorkflowAddRecipeSchema=exports.MetaHookCreateSchema=exports.MetaHookListSchema=exports.MetaRecipeRemoveHookSchema=exports.MetaRecipeAddHookSchema=exports.MetaRecipeCreateSchema=exports.MetaRecipeGetSchema=exports.MetaRecipeListSchema=exports.MetaWorkflowUpdateSchema=exports.MetaWorkflowCreateSchema=exports.MetaWorkflowGetSchema=exports.MetaWorkflowListSchema=exports.GenerateRequestJournalSchema=exports.QuickManageSchema=exports.QuickReplaceSchema=exports.QuickWriteSchema=exports.RequestOperationsSchema=exports.ManageFilesSchema=exports.ModifyFileSchema=exports.RevertRequestSchema=exports.SwitchToBranchSchema=void 0
|
|
3365
3238
|
const r=t(1569),n=t(8955),o=r.z.string().refine((e=>!!e&&/^tas\d{6}$/.test(e)),{message:"Task ID must match format: tas###### (e.g. tas000001). If you don't have a task yet, create one first using task_operations with operation 'create'."}),s=r.z.string().refine((e=>!!e&&/^req\d{6}$/.test(e)),{message:"Request ID must match format: req###### (e.g. req000001)"}),i=r.z.string().refine((e=>!!e&&(/^doc_[0-9A-Z]{26}$/i.test(e)||/^(doc|plan|jour)\d{6}$/.test(e))),{message:"Document ID must match format: doc_[26 alphanumeric] (ULID) or doc######/plan######/jour###### (local ID)"})
|
|
3366
|
-
exports.CompletionStatusEnum=r.z.enum(["complete","incomplete","partial"]),exports.TestCoverageTypeEnum=r.z.enum(["unit","e2e","integration","manual"]),exports.RequestTypeEnum=r.z.enum(["feature","bugfix","quick-edit"]),exports.TaskStatusEnum=r.z.enum(["pending","in_progress","ready_for_review","completed","canceled","reverted"]),exports.RequestStatusEnum=r.z.enum(["open","in_progress","ready_for_review","ready_for_merge","completed","canceled","reverted","conflicted"]),exports.CriterionStatusEnum=r.z.enum(["unverified","verified"]),exports.EvidenceTypeEnum=r.z.enum(["test","manual","other"]),exports.RecordTypeEnum=r.z.enum(["write","modify","blocker","resolution","discovery","test","delete"]),exports.AcceptanceCriterionSchema=r.z.object({description:r.z.string(),status:r.z.enum(["unverified","verified"]).default("unverified"),evidence:r.z.string().nullable().optional(),evidenceType:r.z.enum(["test","manual","other"]).nullable().optional(),createdAt:r.z.string().optional(),updatedAt:r.z.string().optional()}),exports.TestDefinitionSchema=r.z.object({id:r.z.string(),description:r.z.string(),status:exports.CompletionStatusEnum,coverageType:exports.TestCoverageTypeEnum,accepts:r.z.array(r.z.string())}),exports.TestVerificationSchema=r.z.object({criteria:r.z.array(r.z.string()),tests:r.z.array(r.z.string()),coverageType:exports.TestCoverageTypeEnum,coverageRatio:r.z.number(),createdAt:r.z.string().optional(),updatedAt:r.z.string().optional()}),exports.ExecutedTestSchema=r.z.object({id:r.z.string(),testId:r.z.string(),status:exports.CompletionStatusEnum,results:r.z.string(),coverage:r.z.array(r.z.string()),executedAt:r.z.string()}),exports.CompleteRequestSchema=r.z.object({status:exports.RequestStatusEnum,acceptanceCriteria:r.z.array(exports.AcceptanceCriterionSchema),testVerification:exports.TestVerificationSchema.optional(),completionSummary:r.z.string().optional()}),exports.CreateRequestSchema=r.z.object({title:r.z.string(),type:r.z.enum(["feature","bugfix"]),description:r.z.string(),acceptanceCriteria:r.z.array(r.z.string()),planDocumentId:r.z.string().optional()}),exports.CreateTaskSchema=r.z.object({requestId:s,title:r.z.string(),description:r.z.string()}),exports.UpdateTaskStatusSchema=r.z.object({taskId:o,status:exports.TaskStatusEnum,note:r.z.string()}),exports.WriteFileSchema=r.z.object({taskId:o,path:r.z.string().optional(),documentId:i.optional(),content:r.z.union([r.z.string(),r.z.record(r.z.any()),r.z.array(r.z.unknown())]),format:r.z.enum(["text","json"]).optional(),append:r.z.boolean().optional(),comment:r.z.string()}).refine((e=>e.path&&!e.documentId||!e.path&&e.documentId),{message:"path or documentId required"}),exports.ViewAssetSchema=r.z.object({filename:r.z.string().describe("The asset filename (e.g., 01JMXYZ.png)")}),exports.ReadFilesSchema=r.z.object({paths:r.z.array(r.z.object({path:r.z.string().optional(),documentId:i.optional(),lines:r.z.string().optional()}).refine((e=>e.path&&!e.documentId||!e.path&&e.documentId),{message:"path or documentId required"})),encoding:r.z.enum(["utf8","utf-8","ascii","binary"]).optional()}),exports.ListDirectorySchema=r.z.object({path:r.z.string(),levels:r.z.number().min(1).max(4).optional(),sortBy:r.z.enum(["name","modified","size","type"]).optional()}),exports.GetFileInfoSchema=r.z.object({path:r.z.string()}),exports.CreateDirectorySchema=r.z.object({path:r.z.string(),taskId:o,comment:r.z.string().optional()}),exports.MoveFilesSchema=r.z.object({taskId:o,operations:r.z.array(r.z.object({source:r.z.string(),destination:r.z.string()})),comment:r.z.string()}),exports.ReplaceStringSchema=r.z.object({taskId:o,path:r.z.string(),replacements:r.z.array(r.z.object({old_str:r.z.string(),new_str:r.z.string()})),mode:r.z.enum(["unique","all"]).optional(),comment:r.z.string()}),exports.ReplaceStringsSchema=r.z.object({taskId:o,operations:r.z.array(r.z.object({path:r.z.string().optional(),documentId:i.optional(),replacements:r.z.array(r.z.object({old_str:r.z.string(),new_str:r.z.string()})),mode:r.z.enum(["unique","all"]).optional()}).refine((e=>e.path&&!e.documentId||!e.path&&e.documentId),{message:"path or documentId required"})),comment:r.z.string()}),exports.ReplaceInFilesSchema=r.z.object({taskId:o,operations:r.z.array(r.z.object({path:r.z.string().optional(),documentId:i.optional(),replacements:r.z.array(r.z.object({old:r.z.string().min(1,"old string cannot be empty"),new:r.z.string(),match_mode:r.z.enum(["unique","all"]).optional()})).min(1,"At least one replacement required"),fuzzy_match:r.z.boolean().optional()}).refine((e=>e.path&&!e.documentId||!e.path&&e.documentId),{message:"Either path or documentId is required, but not both"})).min(1,"At least one operation required"),fuzzy_match:r.z.boolean().optional().default(!0),comment:r.z.string()}),exports.
|
|
3239
|
+
exports.CompletionStatusEnum=r.z.enum(["complete","incomplete","partial"]),exports.TestCoverageTypeEnum=r.z.enum(["unit","e2e","integration","manual"]),exports.RequestTypeEnum=r.z.enum(["feature","bugfix","quick-edit"]),exports.TaskStatusEnum=r.z.enum(["pending","in_progress","ready_for_review","completed","canceled","reverted"]),exports.RequestStatusEnum=r.z.enum(["open","in_progress","ready_for_review","ready_for_merge","completed","canceled","reverted","conflicted"]),exports.CriterionStatusEnum=r.z.enum(["unverified","verified"]),exports.EvidenceTypeEnum=r.z.enum(["test","manual","other"]),exports.RecordTypeEnum=r.z.enum(["write","modify","blocker","resolution","discovery","test","delete"]),exports.AcceptanceCriterionSchema=r.z.object({description:r.z.string(),status:r.z.enum(["unverified","verified"]).default("unverified"),evidence:r.z.string().nullable().optional(),evidenceType:r.z.enum(["test","manual","other"]).nullable().optional(),createdAt:r.z.string().optional(),updatedAt:r.z.string().optional()}),exports.TestDefinitionSchema=r.z.object({id:r.z.string(),description:r.z.string(),status:exports.CompletionStatusEnum,coverageType:exports.TestCoverageTypeEnum,accepts:r.z.array(r.z.string())}),exports.TestVerificationSchema=r.z.object({criteria:r.z.array(r.z.string()),tests:r.z.array(r.z.string()),coverageType:exports.TestCoverageTypeEnum,coverageRatio:r.z.number(),createdAt:r.z.string().optional(),updatedAt:r.z.string().optional()}),exports.ExecutedTestSchema=r.z.object({id:r.z.string(),testId:r.z.string(),status:exports.CompletionStatusEnum,results:r.z.string(),coverage:r.z.array(r.z.string()),executedAt:r.z.string()}),exports.CompleteRequestSchema=r.z.object({status:exports.RequestStatusEnum,acceptanceCriteria:r.z.array(exports.AcceptanceCriterionSchema),testVerification:exports.TestVerificationSchema.optional(),completionSummary:r.z.string().optional()}),exports.CreateRequestSchema=r.z.object({title:r.z.string(),type:r.z.enum(["feature","bugfix"]),description:r.z.string(),acceptanceCriteria:r.z.array(r.z.string()),planDocumentId:r.z.string().optional()}),exports.CreateTaskSchema=r.z.object({requestId:s,title:r.z.string(),description:r.z.string()}),exports.UpdateTaskStatusSchema=r.z.object({taskId:o,status:exports.TaskStatusEnum,note:r.z.string()}),exports.WriteFileSchema=r.z.object({taskId:o,path:r.z.string().optional(),documentId:i.optional(),content:r.z.union([r.z.string(),r.z.record(r.z.any()),r.z.array(r.z.unknown())]),format:r.z.enum(["text","json"]).optional(),append:r.z.boolean().optional(),comment:r.z.string()}).refine((e=>e.path&&!e.documentId||!e.path&&e.documentId),{message:"path or documentId required"}),exports.ViewAssetSchema=r.z.object({filename:r.z.string().describe("The asset filename (e.g., 01JMXYZ.png)")}),exports.ReadFilesSchema=r.z.object({paths:r.z.array(r.z.object({path:r.z.string().optional(),documentId:i.optional(),lines:r.z.string().optional()}).refine((e=>e.path&&!e.documentId||!e.path&&e.documentId),{message:"path or documentId required"})),encoding:r.z.enum(["utf8","utf-8","ascii","binary"]).optional()}),exports.ListDirectorySchema=r.z.object({path:r.z.string(),levels:r.z.number().min(1).max(4).optional(),sortBy:r.z.enum(["name","modified","size","type"]).optional()}),exports.GetFileInfoSchema=r.z.object({path:r.z.string()}),exports.CreateDirectorySchema=r.z.object({path:r.z.string(),taskId:o,comment:r.z.string().optional()}),exports.MoveFilesSchema=r.z.object({taskId:o,operations:r.z.array(r.z.object({source:r.z.string(),destination:r.z.string()})),comment:r.z.string()}),exports.ReplaceStringSchema=r.z.object({taskId:o,path:r.z.string(),replacements:r.z.array(r.z.object({old_str:r.z.string(),new_str:r.z.string()})),mode:r.z.enum(["unique","all"]).optional(),comment:r.z.string()}),exports.ReplaceStringsSchema=r.z.object({taskId:o,operations:r.z.array(r.z.object({path:r.z.string().optional(),documentId:i.optional(),replacements:r.z.array(r.z.object({old_str:r.z.string(),new_str:r.z.string()})),mode:r.z.enum(["unique","all"]).optional()}).refine((e=>e.path&&!e.documentId||!e.path&&e.documentId),{message:"path or documentId required"})),comment:r.z.string()}),exports.ReplaceInFilesSchema=r.z.object({taskId:o,operations:r.z.array(r.z.object({path:r.z.string().optional(),documentId:i.optional(),replacements:r.z.array(r.z.object({old:r.z.string().min(1,"old string cannot be empty"),new:r.z.string(),match_mode:r.z.enum(["unique","all"]).optional()})).min(1,"At least one replacement required"),fuzzy_match:r.z.boolean().optional()}).refine((e=>e.path&&!e.documentId||!e.path&&e.documentId),{message:"Either path or documentId is required, but not both"})).min(1,"At least one operation required"),fuzzy_match:r.z.boolean().optional().default(!0),comment:r.z.string()}),exports.DeleteFileSchema=r.z.object({taskId:o,path:r.z.string(),comment:r.z.string()}),exports.DeleteFilesSchema=r.z.object({taskId:o,paths:r.z.array(r.z.string()).optional(),operations:r.z.array(r.z.object({path:r.z.string().optional(),documentId:i.optional()}).refine((e=>e.path&&!e.documentId||!e.path&&e.documentId),{message:"path or documentId required"})).optional(),comment:r.z.string()}).refine((e=>e.paths&&!e.operations||!e.paths&&e.operations),{message:"paths or operations required"}).refine((e=>e.paths?.length||e.operations?.length),{message:"path/operation required"}),exports.FileHistorySchema=r.z.object({path:r.z.string(),limit:r.z.number().min(1).max(100).default(10),showDiff:r.z.boolean().default(!1),showTraceability:r.z.boolean().default(!0),branch:r.z.string().optional(),commit:r.z.string().optional(),since:r.z.string().optional()}),exports.FileRecoverSchema=r.z.object({taskId:o,path:r.z.string(),commitHash:r.z.string(),createBackup:r.z.boolean().default(!0)}),exports.QueryHistorySchema=r.z.object({queryType:r.z.enum(["file-history","request-file-history","recover","blame"],{errorMap(){return{message:"Invalid queryType. Valid options: file-history, request-file-history, recover, blame"}}}),fileHistory:r.z.object({path:r.z.string(),limit:r.z.number().min(1).max(100).default(10),showDiff:r.z.boolean().default(!1),showTraceability:r.z.boolean().default(!0),branch:r.z.string().optional(),commit:r.z.string().optional(),since:r.z.string().optional()}).optional(),requestHistory:r.z.object({requestId:s,detailLevel:r.z.enum(["summary","detailed"]).default("summary"),taskId:o.optional(),showDiff:r.z.boolean().optional(),fileFilter:r.z.string().optional()}).optional(),recover:r.z.object({taskId:o,path:r.z.string(),commitHash:r.z.string().optional(),createBackup:r.z.boolean().default(!0)}).optional(),blame:r.z.object({path:r.z.string(),lines:r.z.string().optional(),branch:r.z.string().optional()}).optional()}).refine((e=>"file-history"===e.queryType?e.fileHistory&&!e.requestHistory&&!e.recover:"request-file-history"===e.queryType?e.requestHistory&&!e.fileHistory&&!e.recover:"recover"===e.queryType?e.recover&&!e.fileHistory&&!e.requestHistory&&!e.blame:"blame"===e.queryType&&e.blame&&!e.fileHistory&&!e.requestHistory&&!e.recover),{message:"Invalid query data"}),exports.SearchSchema=r.z.object({needle:r.z.string().optional(),directory:r.z.string().optional(),options:r.z.object({caseSensitive:r.z.boolean().optional(),fileExtension:r.z.string().optional(),maxResults:r.z.number().optional(),useRegex:r.z.boolean().optional(),searchIn:r.z.enum(["content","filename","both"]).default("content").optional(),contextLines:r.z.number().min(0).max(10).optional(),levels:r.z.number().min(1).max(4).optional(),sortBy:r.z.enum(["name","modified","size","type"]).optional()}).optional()}),exports.ListTasksSchema=r.z.object({requestId:s,filters:r.z.object({status:r.z.enum(["pending","in_progress","ready_for_review","completed","canceled","reverted"]).optional(),limit:r.z.number().min(1).max(100).default(20),offset:r.z.number().min(0).default(0),sortBy:r.z.enum(["created","updated"]).default("updated"),sortDirection:r.z.enum(["asc","desc"]).default("desc")}).optional()}),exports.ListRequestsSchema=r.z.object({filters:r.z.object({type:r.z.enum(["feature","bugfix"]).optional(),status:r.z.enum(["open","in_progress","ready_for_review","completed","canceled"]).optional(),planDocumentId:r.z.string().optional(),dateFrom:r.z.string().optional(),dateTo:r.z.string().optional(),limit:r.z.number().min(1).max(100).default(20),offset:r.z.number().min(0).default(0),sortBy:r.z.enum(["created","updated"]).default("updated"),sortDirection:r.z.enum(["asc","desc"]).default("desc")}).optional()}),exports.GetRequestInformationSchema=r.z.object({requestId:s}),exports.GetTaskInformationSchema=r.z.object({taskId:o}),exports.CompleteTaskSchema=r.z.object({taskId:o,summary:r.z.string()}),exports.TaskOperationsSchema=r.z.object({operation:r.z.enum(["get-info","list"]),taskId:o.optional(),requestId:s.optional(),status:r.z.enum(["pending","in_progress","ready_for_review","completed","canceled","reverted"]).optional(),limit:r.z.number().min(1).max(100).default(20),offset:r.z.number().min(0).default(0),sortBy:r.z.enum(["created","updated"]).default("updated"),sortDirection:r.z.enum(["asc","desc"]).default("desc")}).superRefine(((e,t)=>{"get-info"!==e.operation||e.taskId||t.addIssue({code:"custom",message:'taskId is required for get-info. Example: { "operation": "get-info", "taskId": "tas000001" }'}),"list"!==e.operation||e.requestId||t.addIssue({code:"custom",message:'requestId is required for list. Example: { "operation": "list", "requestId": "req000001" }'})}))
|
|
3367
3240
|
const a=r.z.string().min(1).describe("OpenCode session ID")
|
|
3368
3241
|
exports.SubagentOperationsSchema=r.z.object({sessionId:a.optional(),operation:r.z.enum(["spawn","continue","check-status","abort","read-messages","list-sessions"]),spawn:r.z.object({agent:r.z.string().default("work").refine((e=>(0,n.isValidAgent)(e)),{message:"Invalid agent. Check tool description for available agents."}).describe("The subagent type to spawn (see tool description for available agents)"),prompt:r.z.string().min(1).describe("The task/prompt for the subagent to work on"),description:r.z.string().max(60).describe('Brief label for the UI, e.g. "Plan auth refactor" (max 60 chars)'),requestId:r.z.string().regex(/^req\d{6}$/).optional().describe("Optional request ID to associate with the work"),allowParallel:r.z.boolean().default(!1).optional().describe("Allow spawning even if request already has active workers (default: false, will block)"),useExistingSession:r.z.string().optional().describe("Optional existing session ID to send prompt to instead of creating new session")}).optional(),continue:r.z.object({prompt:r.z.string().min(1).describe("New instructions/feedback to send to the subagent")}).optional(),readMessages:r.z.object({limit:r.z.number().min(1).max(50).default(1).describe("Number of recent messages to fetch (default 10, max 50)")}).optional(),listSessions:r.z.object({activeOnly:r.z.boolean().default(!1).describe("Only show sessions that are currently active/busy"),requestId:r.z.string().optional().describe("Find sessions that worked on a specific request"),limit:r.z.number().min(1).max(100).optional().describe("Only show N most recent sessions"),minTokens:r.z.number().min(0).optional().describe("Only show sessions with at least this many tokens"),maxTokens:r.z.number().min(0).optional().describe("Only show sessions with at most this many tokens"),maxAgeHours:r.z.number().min(0).optional().describe("Only show sessions newer than X hours")}).optional()}).refine((e=>{const t=!!e.sessionId,r=!!e.spawn,n=!!e.continue,o=!!e.readMessages
|
|
3369
|
-
return"spawn"===e.operation?r&&!n&&!o:"continue"===e.operation?n&&!r&&!o&&t:"check-status"===e.operation||"abort"===e.operation?!r&&!n&&!o&&t:"read-messages"===e.operation?!r&&!n&&t:"list-sessions"===e.operation&&!(r||n||o||t)}),{message:"Invalid operation data: spawn requires spawn object, continue/check-status/abort/read-messages require sessionId"}),exports.SpecialistOpsSchema=r.z.object({operation:r.z.enum(["delegate","follow-up","check-status","list","abort"]),sessionId:a.optional(),delegate:r.z.object({prompt:r.z.string().min(1).describe("Detailed instructions for the specialist"),description:r.z.string().max(60).describe("Brief label for the UI (max 60 chars)"),requestId:r.z.string().regex(/^req\d{6}$/).describe("Request ID to associate with the work").optional(),specialization:r.z.string().max(
|
|
3242
|
+
return"spawn"===e.operation?r&&!n&&!o:"continue"===e.operation?n&&!r&&!o&&t:"check-status"===e.operation||"abort"===e.operation?!r&&!n&&!o&&t:"read-messages"===e.operation?!r&&!n&&t:"list-sessions"===e.operation&&!(r||n||o||t)}),{message:"Invalid operation data: spawn requires spawn object, continue/check-status/abort/read-messages require sessionId"}),exports.SpecialistOpsSchema=r.z.object({operation:r.z.enum(["delegate","follow-up","check-status","list","abort"]),sessionId:a.optional(),delegate:r.z.object({prompt:r.z.string().min(1).describe("Detailed instructions for the specialist"),description:r.z.string().max(60).describe("Brief label for the UI (max 60 chars)"),requestId:r.z.string().regex(/^req\d{6}$/).describe("Request ID to associate with the work").optional(),specialization:r.z.string().max(500).describe('Domain description for the specialist (e.g. "Frontend UI components", "Database migrations")')}).optional(),followUp:r.z.object({prompt:r.z.string().min(1).describe("Follow-up instructions or feedback for the specialist"),specialization:r.z.string().max(500).describe("Update the specialist's domain description if their focus has shifted").optional()}).optional(),list:r.z.object({activeOnly:r.z.boolean().default(!1).describe("Only show active/busy specialists"),requestId:r.z.string().optional().describe("Filter to specialists working on a specific request"),limit:r.z.number().min(1).max(100).optional().describe("Max sessions to return")}).optional()}).refine((e=>{const t=!!e.sessionId,r=!!e.delegate,n=!!e.followUp
|
|
3370
3243
|
return"delegate"===e.operation?r&&!n&&!t:"follow-up"===e.operation?n&&!r&&t:"check-status"===e.operation||"abort"===e.operation?!r&&!n&&t:"list"===e.operation&&!r&&!n&&!t}),{message:"Invalid operation data: delegate requires delegate object, follow-up/check-status/abort require sessionId"}),exports.PlannerOpsSchema=r.z.object({operation:r.z.enum(["request","check-status","list"]),request:r.z.object({prompt:r.z.string().min(1).describe("What to plan \u2014 feature description, architecture question, etc."),description:r.z.string().max(60).describe("Brief label for the UI (max 60 chars)")}).optional(),sessionId:a.optional(),list:r.z.object({activeOnly:r.z.boolean().default(!1).describe("Only show active/busy planning sessions"),limit:r.z.number().min(1).max(100).optional().describe("Max sessions to return")}).optional()}).refine((e=>{const t=!!e.request,r=!!e.sessionId
|
|
3371
3244
|
return"request"===e.operation?t&&!r:"check-status"===e.operation?!t&&r:"list"===e.operation&&!t&&!r}),{message:"Invalid operation data: request requires request object, check-status requires sessionId"}),exports.SwitchToRequestBranchSchema=r.z.object({requestId:s}),exports.InsertLinesSchema=r.z.object({taskId:o,operations:r.z.array(r.z.object({path:r.z.string().optional(),documentId:i.optional(),insertions:r.z.array(r.z.object({type:r.z.enum(["before","after","between"]),line:r.z.number().optional(),afterLine:r.z.number().optional(),beforeLine:r.z.number().optional(),content:r.z.union([r.z.string(),r.z.array(r.z.string())])}).refine((e=>"between"===e.type?void 0!==e.afterLine&&void 0!==e.beforeLine&&void 0===e.line:void 0!==e.line&&void 0===e.afterLine&&void 0===e.beforeLine),{message:"Invalid line parameters"}))}).refine((e=>e.path&&!e.documentId||!e.path&&e.documentId),{message:"path or documentId required"})),comment:r.z.string()}),exports.ReplaceLinesSchema=r.z.object({taskId:o,operations:r.z.array(r.z.object({path:r.z.string().optional(),documentId:i.optional(),replacements:r.z.array(r.z.object({lines:r.z.string(),content:r.z.union([r.z.string(),r.z.array(r.z.string())])}))}).refine((e=>e.path&&!e.documentId||!e.path&&e.documentId),{message:"path or documentId required"})),comment:r.z.string()}),exports.CreateDocumentSchema=r.z.object({requestId:s.optional(),filename:r.z.string().refine((e=>e.toLowerCase().endsWith(".md")),{message:"Filename must end with .md extension"}),content:r.z.string(),type:r.z.enum(["Report","Documentation","Plan","Other"],{errorMap(){return{message:"Document type must be one of: Report, Documentation, Plan, Other"}}}),comment:r.z.string()}),exports.SearchDocumentsSchema=r.z.object({query:r.z.string(),type:r.z.enum(["Report","Documentation","Plan","Other"]).optional(),requestId:s.optional(),includeArchived:r.z.boolean().default(!1),maxResults:r.z.number().min(1).max(100).default(20),dateFrom:r.z.string().optional(),dateTo:r.z.string().optional(),searchIn:r.z.enum(["content","filename","both"]).default("both")}),exports.DocumentOperationsSchema=r.z.object({operation:r.z.enum(["create","search","create-snapshot","get-history","get-version","restore-version","list-annotations","create-annotation","reply-to-annotation","resolve-annotation"]),documentId:i.optional(),requestId:s.optional(),filename:r.z.string().optional(),content:r.z.string().optional(),type:r.z.enum(["Report","Documentation","Plan","Other"]).optional(),comment:r.z.string().optional(),query:r.z.string().optional(),includeArchived:r.z.boolean().default(!1),maxResults:r.z.number().min(1).max(100).default(20),dateFrom:r.z.string().optional(),dateTo:r.z.string().optional(),searchIn:r.z.enum(["content","filename","both"]).default("both"),versionLabel:r.z.string().optional(),changeSummary:r.z.string().optional(),versionNumber:r.z.number().int().min(1).optional(),selectedText:r.z.string().optional(),prefixContext:r.z.string().optional(),suffixContext:r.z.string().optional(),lineHint:r.z.number().int().optional(),body:r.z.string().optional(),annotationId:r.z.string().optional()}).superRefine(((e,t)=>{const r=e.operation;["create-snapshot","get-history","get-version","restore-version","list-annotations","create-annotation","reply-to-annotation","resolve-annotation"].includes(r)&&!e.documentId&&t.addIssue({code:"custom",message:`documentId is required for '${r}'. Example: { "operation": "${r}", "documentId": "doc000001" }`}),"create"===r&&(e.filename?e.filename.toLowerCase().endsWith(".md")||t.addIssue({code:"custom",message:"Filename must end with .md extension"}):t.addIssue({code:"custom",message:"filename is required for create (must end with .md)"}),e.content||t.addIssue({code:"custom",message:"content is required for create"}),e.type||t.addIssue({code:"custom",message:"type is required for create (Report, Documentation, Plan, or Other)"}),e.comment||t.addIssue({code:"custom",message:"comment is required for create"})),"search"!==r||e.query||t.addIssue({code:"custom",message:'query is required for search. Example: { "operation": "search", "query": "search term" }'}),"get-version"!==r&&"restore-version"!==r||e.versionNumber||t.addIssue({code:"custom",message:`versionNumber is required for '${r}'`}),"create-annotation"===r&&(e.selectedText||t.addIssue({code:"custom",message:"selectedText is required for create-annotation"}),e.body||t.addIssue({code:"custom",message:"body is required for create-annotation"})),"reply-to-annotation"===r&&(e.annotationId||t.addIssue({code:"custom",message:"annotationId is required for reply-to-annotation"}),e.body||t.addIssue({code:"custom",message:"body is required for reply-to-annotation"})),"resolve-annotation"!==r||e.annotationId||t.addIssue({code:"custom",message:"annotationId is required for resolve-annotation"})}))
|
|
3372
3245
|
const c=r.z.string().refine((e=>!!e&&(/^doc_[0-9A-Z]{26}$/i.test(e)||/^plan\d{6}$/.test(e))),{message:"Plan ID must match format: doc_[26 alphanumeric] (ULID) or plan###### (local ID)"})
|
|
3373
3246
|
exports.PlanReadSchema=r.z.object({operation:r.z.enum(["get","get-active","list","get-history","get-requests"]),planId:c.optional(),searchQuery:r.z.string().optional(),limit:r.z.number().min(1).max(100).default(20),offset:r.z.number().min(0).default(0),sortBy:r.z.enum(["createdAt","updatedAt","filename"]).default("updatedAt"),sortDirection:r.z.enum(["ASC","DESC"]).default("DESC")}).superRefine(((e,t)=>{["get","get-history","get-requests"].includes(e.operation)&&!e.planId&&t.addIssue({code:"custom",message:`planId is required for '${e.operation}'. Example: { "operation": "${e.operation}", "planId": "plan000001" }`})})),exports.PlanWriteSchema=r.z.object({operation:r.z.enum(["update","append","replace","create-snapshot","restore","set-active"]),planId:c,content:r.z.string().optional(),name:r.z.string().optional().describe("Optional new name for the plan"),old:r.z.string().optional().describe("Text to find in the plan (for replace)"),new:r.z.string().optional().describe("Replacement text (for replace)"),versionLabel:r.z.string().optional(),changeSummary:r.z.string().optional(),versionNumber:r.z.number().int().min(1).optional()}).superRefine(((e,t)=>{const r=e.operation
|
|
3374
|
-
"update"!==r&&"append"!==r||e.content||t.addIssue({code:"custom",message:`content is required for '${r}'. Example: { "operation": "${r}", "planId": "plan000001", "content": "..." }`}),"replace"===r&&(e.old||t.addIssue({code:"custom",message:'old is required for replace. Example: { "operation": "replace", "planId": "plan000001", "old": "find this", "new": "replace with" }'}),void 0===e.new&&t.addIssue({code:"custom",message:"new is required for replace"})),"restore"!==r||e.versionNumber||t.addIssue({code:"custom",message:'versionNumber is required for restore. Example: { "operation": "restore", "planId": "plan000001", "versionNumber": 1 }'})})),exports.SwitchToMainBranchSchema=r.z.object({}),exports.SwitchToBranchSchema=r.z.object({branch:r.z.string().optional(),password:r.z.string().optional()}),exports.RevertRequestSchema=r.z.object({requestId:s,reason:r.z.string(),confirmDestructive:r.z.boolean().optional()}),exports.ModifyFileSchema=r.z.object({taskId:o,operations:r.z.array(r.z.object({path:r.z.string().optional(),documentId:i.optional(),operationType:r.z.enum(["replace-string","insert-lines","replace-lines","delete-string","delete-lines"]),replaceString:r.z.object({replacements:r.z.array(r.z.object({old_str:r.z.string(),new_str:r.z.string()})),mode:r.z.enum(["unique","all"]).optional()}).optional(),insertLines:r.z.object({insertions:r.z.array(r.z.object({type:r.z.enum(["before","after","between"]),line:r.z.number().optional(),afterLine:r.z.number().optional(),beforeLine:r.z.number().optional(),content:r.z.union([r.z.string(),r.z.array(r.z.string())])}).refine((e=>"between"===e.type?void 0!==e.afterLine&&void 0!==e.beforeLine&&void 0===e.line:void 0!==e.line&&void 0===e.afterLine&&void 0===e.beforeLine),{message:"Invalid line parameters"}))}).optional(),replaceLines:r.z.object({replacements:r.z.array(r.z.object({lines:r.z.string(),content:r.z.union([r.z.string(),r.z.array(r.z.string())])}))}).optional(),deleteString:r.z.object({patterns:r.z.array(r.z.string()),mode:r.z.enum(["all","unique"]).optional()}).optional(),deleteLines:r.z.object({lines:r.z.string()}).optional()}).refine((e=>e.path&&!e.documentId||!e.path&&e.documentId),{message:"path or documentId required"}).refine((e=>"replace-string"===e.operationType?e.replaceString&&!e.insertLines&&!e.replaceLines&&!e.deleteString&&!e.deleteLines:"insert-lines"===e.operationType?e.insertLines&&!e.replaceString&&!e.replaceLines&&!e.deleteString&&!e.deleteLines:"replace-lines"===e.operationType?e.replaceLines&&!e.replaceString&&!e.insertLines&&!e.deleteString&&!e.deleteLines:"delete-string"===e.operationType?e.deleteString&&!e.replaceString&&!e.insertLines&&!e.replaceLines&&!e.deleteLines:"delete-lines"===e.operationType&&e.deleteLines&&!e.replaceString&&!e.insertLines&&!e.replaceLines&&!e.deleteString),{message:"Invalid operation data"})),comment:r.z.string()}),exports.ManageFilesSchema=r.z.object({taskId:o,operations:r.z.array(r.z.object({operationType:r.z.enum(["create-directory","move-files","delete-files","get-file-info"]),createDirectory:r.z.object({path:r.z.string()}).optional(),moveFiles:r.z.object({moves:r.z.array(r.z.object({source:r.z.string(),destination:r.z.string()}))}).optional(),deleteFiles:r.z.object({targets:r.z.array(r.z.object({path:r.z.string().optional(),documentId:i.optional()}).refine((e=>e.path&&!e.documentId||!e.path&&e.documentId),{message:"path or documentId required"}))}).optional(),getFileInfo:r.z.object({path:r.z.string()}).optional()}).refine((e=>"create-directory"===e.operationType?e.createDirectory&&!e.moveFiles&&!e.deleteFiles&&!e.getFileInfo:"move-files"===e.operationType?e.moveFiles&&!e.createDirectory&&!e.deleteFiles&&!e.getFileInfo:"delete-files"===e.operationType?e.deleteFiles&&!e.createDirectory&&!e.moveFiles&&!e.getFileInfo:"get-file-info"===e.operationType&&e.getFileInfo&&!e.createDirectory&&!e.moveFiles&&!e.deleteFiles),{message:"Invalid operation data"})),comment:r.z.string()}),exports.RequestOperationsSchema=r.z.object({requestId:s.optional(),operation:r.z.enum(["complete","merge","approve","revert","get-info","list","search"]),complete:r.z.preprocess((e=>"string"==typeof e?(()=>{try{return JSON.parse(e)}catch{return e}})():e),r.z.object({summary:r.z.string()})).optional(),merge:r.z.preprocess((e=>"string"==typeof e?(()=>{try{return JSON.parse(e)}catch{return e}})():e),r.z.object({verifications:r.z.array(r.z.object({key:r.z.string().min(2).max(4),evidence:r.z.string().min(1)})).min(1)})).optional(),revert:r.z.object({reason:r.z.string(),confirmDestructive:r.z.boolean().optional()}).optional(),list:r.z.object({filters:r.z.object({type:r.z.enum(["feature","bugfix"]).optional(),status:r.z.enum(["pending_approval","open","in_progress","ready_for_review","ready_for_merge","resolving_conflicts","completed","canceled"]).optional(),dateFrom:r.z.string().optional(),dateTo:r.z.string().optional(),limit:r.z.number().min(1).max(100).default(20),offset:r.z.number().min(0).default(0),sortBy:r.z.enum(["created","updated"]).default("updated"),sortDirection:r.z.enum(["asc","desc"]).default("desc")}).optional()}).optional(),search:r.z.object({query:r.z.string().min(1),searchIn:r.z.enum(["title","description","criteria","all"]).default("all"),filters:r.z.object({type:r.z.enum(["feature","bugfix"]).optional(),status:r.z.enum(["pending_approval","open","in_progress","ready_for_review","ready_for_merge","resolving_conflicts","completed","canceled"]).optional(),dateFrom:r.z.string().optional(),dateTo:r.z.string().optional(),limit:r.z.number().min(1).max(100).default(20),offset:r.z.number().min(0).default(0)}).optional()}).optional(),approve:r.z.object({}).optional()}).superRefine(((e,t)=>{const r=!!e.requestId,n=e.operation
|
|
3247
|
+
"update"!==r&&"append"!==r||e.content||t.addIssue({code:"custom",message:`content is required for '${r}'. Example: { "operation": "${r}", "planId": "plan000001", "content": "..." }`}),"replace"===r&&(e.old||t.addIssue({code:"custom",message:'old is required for replace. Example: { "operation": "replace", "planId": "plan000001", "old": "find this", "new": "replace with" }'}),void 0===e.new&&t.addIssue({code:"custom",message:"new is required for replace"})),"restore"!==r||e.versionNumber||t.addIssue({code:"custom",message:'versionNumber is required for restore. Example: { "operation": "restore", "planId": "plan000001", "versionNumber": 1 }'})})),exports.SwitchToMainBranchSchema=r.z.object({}),exports.SwitchToBranchSchema=r.z.object({branch:r.z.string().optional(),password:r.z.string().optional()}),exports.RevertRequestSchema=r.z.object({requestId:s,reason:r.z.string(),confirmDestructive:r.z.boolean().optional()}),exports.ModifyFileSchema=r.z.object({taskId:o,operations:r.z.array(r.z.object({path:r.z.string().optional(),documentId:i.optional(),operationType:r.z.enum(["replace-string","insert-lines","replace-lines","delete-string","delete-lines"]),replaceString:r.z.object({replacements:r.z.array(r.z.object({old_str:r.z.string(),new_str:r.z.string()})),mode:r.z.enum(["unique","all"]).optional()}).optional(),insertLines:r.z.object({insertions:r.z.array(r.z.object({type:r.z.enum(["before","after","between"]),line:r.z.number().optional(),afterLine:r.z.number().optional(),beforeLine:r.z.number().optional(),content:r.z.union([r.z.string(),r.z.array(r.z.string())])}).refine((e=>"between"===e.type?void 0!==e.afterLine&&void 0!==e.beforeLine&&void 0===e.line:void 0!==e.line&&void 0===e.afterLine&&void 0===e.beforeLine),{message:"Invalid line parameters"}))}).optional(),replaceLines:r.z.object({replacements:r.z.array(r.z.object({lines:r.z.string(),content:r.z.union([r.z.string(),r.z.array(r.z.string())])}))}).optional(),deleteString:r.z.object({patterns:r.z.array(r.z.string()),mode:r.z.enum(["all","unique"]).optional()}).optional(),deleteLines:r.z.object({lines:r.z.string()}).optional()}).refine((e=>e.path&&!e.documentId||!e.path&&e.documentId),{message:"path or documentId required"}).refine((e=>"replace-string"===e.operationType?e.replaceString&&!e.insertLines&&!e.replaceLines&&!e.deleteString&&!e.deleteLines:"insert-lines"===e.operationType?e.insertLines&&!e.replaceString&&!e.replaceLines&&!e.deleteString&&!e.deleteLines:"replace-lines"===e.operationType?e.replaceLines&&!e.replaceString&&!e.insertLines&&!e.deleteString&&!e.deleteLines:"delete-string"===e.operationType?e.deleteString&&!e.replaceString&&!e.insertLines&&!e.replaceLines&&!e.deleteLines:"delete-lines"===e.operationType&&e.deleteLines&&!e.replaceString&&!e.insertLines&&!e.replaceLines&&!e.deleteString),{message:"Invalid operation data"})),comment:r.z.string()}),exports.ManageFilesSchema=r.z.object({taskId:o,operations:r.z.array(r.z.object({operationType:r.z.enum(["create-directory","move-files","delete-files","get-file-info"]),createDirectory:r.z.object({path:r.z.string()}).optional(),moveFiles:r.z.object({moves:r.z.array(r.z.object({source:r.z.string(),destination:r.z.string()}))}).optional(),deleteFiles:r.z.object({targets:r.z.array(r.z.object({path:r.z.string().optional(),documentId:i.optional()}).refine((e=>e.path&&!e.documentId||!e.path&&e.documentId),{message:"path or documentId required"}))}).optional(),getFileInfo:r.z.object({path:r.z.string()}).optional()}).refine((e=>"create-directory"===e.operationType?e.createDirectory&&!e.moveFiles&&!e.deleteFiles&&!e.getFileInfo:"move-files"===e.operationType?e.moveFiles&&!e.createDirectory&&!e.deleteFiles&&!e.getFileInfo:"delete-files"===e.operationType?e.deleteFiles&&!e.createDirectory&&!e.moveFiles&&!e.getFileInfo:"get-file-info"===e.operationType&&e.getFileInfo&&!e.createDirectory&&!e.moveFiles&&!e.deleteFiles),{message:"Invalid operation data"})),comment:r.z.string()}),exports.RequestOperationsSchema=r.z.object({requestId:s.optional(),operation:r.z.enum(["complete","merge","approve","revert","get-info","list","search","delete-empty"]),complete:r.z.preprocess((e=>"string"==typeof e?(()=>{try{return JSON.parse(e)}catch{return e}})():e),r.z.object({summary:r.z.string()})).optional(),merge:r.z.preprocess((e=>"string"==typeof e?(()=>{try{return JSON.parse(e)}catch{return e}})():e),r.z.object({verifications:r.z.array(r.z.object({key:r.z.string().min(2).max(4),evidence:r.z.string().min(1)})).min(1)})).optional(),revert:r.z.object({reason:r.z.string(),confirmDestructive:r.z.boolean().optional()}).optional(),list:r.z.object({filters:r.z.object({type:r.z.enum(["feature","bugfix"]).optional(),status:r.z.enum(["pending_approval","open","in_progress","ready_for_review","ready_for_merge","resolving_conflicts","completed","canceled"]).optional(),dateFrom:r.z.string().optional(),dateTo:r.z.string().optional(),limit:r.z.number().min(1).max(100).default(20),offset:r.z.number().min(0).default(0),sortBy:r.z.enum(["created","updated"]).default("updated"),sortDirection:r.z.enum(["asc","desc"]).default("desc")}).optional()}).optional(),search:r.z.object({query:r.z.string().min(1),searchIn:r.z.enum(["title","description","criteria","all"]).default("all"),filters:r.z.object({type:r.z.enum(["feature","bugfix"]).optional(),status:r.z.enum(["pending_approval","open","in_progress","ready_for_review","ready_for_merge","resolving_conflicts","completed","canceled"]).optional(),dateFrom:r.z.string().optional(),dateTo:r.z.string().optional(),limit:r.z.number().min(1).max(100).default(20),offset:r.z.number().min(0).default(0)}).optional()}).optional(),approve:r.z.object({}).optional()}).superRefine(((e,t)=>{const r=!!e.requestId,n=e.operation
|
|
3375
3248
|
if(["complete","merge","approve","revert","get-info"].includes(n)&&!r)return void t.addIssue({code:"custom",message:`requestId is required for '${n}' operation`})
|
|
3376
3249
|
const o={complete:{field:"complete",hint:'Provide: { complete: { summary: "..." } }'},merge:{field:"merge",hint:'Provide: { merge: { verifications: [{key: "1a", evidence: "..."}] } }'},revert:{field:"revert",hint:'Provide: { revert: { reason: "..." } }'},search:{field:"search",hint:'Provide: { search: { query: "..." } }'}}[n]
|
|
3377
3250
|
o&&!e[o.field]&&t.addIssue({code:"custom",message:`'${n}' operation requires '${o.field}' data. ${o.hint}`})})),exports.QuickWriteSchema=r.z.object({title:r.z.string().min(1,"Title is required"),description:r.z.string().min(1,"Description is required"),path:r.z.string().optional(),documentId:i.optional(),content:r.z.union([r.z.string(),r.z.record(r.z.any()),r.z.array(r.z.unknown())]),format:r.z.enum(["text","json"]).optional(),append:r.z.boolean().optional()}),exports.QuickReplaceSchema=r.z.object({title:r.z.string().min(1,"Title is required"),description:r.z.string().min(1,"Description is required"),operations:r.z.array(r.z.object({path:r.z.string().optional(),documentId:i.optional(),replacements:r.z.array(r.z.object({old:r.z.string().min(1),new:r.z.string(),match_mode:r.z.enum(["unique","all"]).optional()})).min(1),fuzzy_match:r.z.boolean().optional()})).min(1),fuzzy_match:r.z.boolean().optional(),comment:r.z.string().min(1,"Comment describing the change is required")}),exports.QuickManageSchema=r.z.object({title:r.z.string().min(1,"Title is required"),description:r.z.string().min(1,"Description is required"),operations:r.z.array(r.z.object({operationType:r.z.enum(["create-directory","move-files","delete-files"]),createDirectory:r.z.object({path:r.z.string()}).optional(),moveFiles:r.z.object({moves:r.z.array(r.z.object({source:r.z.string(),destination:r.z.string()}))}).optional(),deleteFiles:r.z.object({targets:r.z.array(r.z.object({path:r.z.string().optional(),documentId:i.optional()}))}).optional()})).min(1)}),exports.GenerateRequestJournalSchema=r.z.object({requestId:r.z.string().regex(/^req[_\d].+$/,"Invalid request ID format. Expected format: req_[26 chars] or req######")}),exports.MetaWorkflowListSchema=r.z.object({}),exports.MetaWorkflowGetSchema=r.z.object({workflowId:r.z.string().describe("Workflow ID to retrieve")}),exports.MetaWorkflowCreateSchema=r.z.object({name:r.z.string().min(1).describe("Unique name for the workflow"),shortName:r.z.string().min(1).max(10).describe("Short display name (required, max 10 chars)"),description:r.z.string().optional().describe("Description of what the workflow does"),documentation:r.z.string().optional().describe("Detailed documentation"),defaultAgent:r.z.string().optional().describe("Default agent template to use"),completionMode:r.z.enum(["auto-merge","auto-test-then-merge","manual-review"]).optional().describe("Request completion behavior: auto-merge (default), auto-test-then-merge, or manual-review"),approvalMode:r.z.enum(["none","require-approval"]).optional().describe("Pre-work approval: none (default) or require-approval")}),exports.MetaWorkflowUpdateSchema=r.z.object({workflowId:r.z.string().describe("Workflow ID to update"),name:r.z.string().min(1).optional().describe("New name"),shortName:r.z.string().max(10).optional().describe("New short name (max 10 chars)"),description:r.z.string().optional().describe("New description"),documentation:r.z.string().optional().describe("New documentation"),defaultAgent:r.z.string().optional().describe("New default agent"),completionMode:r.z.enum(["auto-merge","auto-test-then-merge","manual-review"]).optional().describe("Request completion behavior"),approvalMode:r.z.enum(["none","require-approval"]).optional().describe("Pre-work approval: none (default) or require-approval")}),exports.MetaRecipeListSchema=r.z.object({}),exports.MetaRecipeGetSchema=r.z.object({recipeId:r.z.string().describe("Recipe ID to retrieve")}),exports.MetaRecipeCreateSchema=r.z.object({name:r.z.string().min(1).describe("Unique name for the recipe"),description:r.z.string().optional().describe("Description of what the recipe does"),documentation:r.z.string().optional().describe("Detailed documentation")}),exports.MetaRecipeAddHookSchema=r.z.object({recipeId:r.z.string().describe("Recipe ID to add the hook to"),hookId:r.z.string().describe("Hook template ID to add"),position:r.z.number().int().min(0).optional().describe("Position in the recipe (0-based, appended if omitted)")}),exports.MetaRecipeRemoveHookSchema=r.z.object({recipeId:r.z.string().describe("Recipe ID to remove the hook from"),hookId:r.z.string().describe("Hook template ID to remove")}),exports.MetaHookListSchema=r.z.object({}),exports.MetaHookCreateSchema=r.z.object({name:r.z.string().min(1).describe("Unique name for the hook"),description:r.z.string().optional().describe("Description of what the hook does"),eventType:r.z.string().describe("Event type that triggers this hook (e.g., session_idle, request_completed, custom:plan_ready)"),category:r.z.enum(["alchemy","session","message","editing","reading","file_management","documents","history","tool"]).default("session").describe("Hook category"),agent:r.z.string().describe("Agent template to execute when hook fires"),promptTemplate:r.z.string().describe("Prompt template with {{variable}} substitution"),condition:r.z.record(r.z.any()).optional().describe("Condition object for filtering when hook fires"),executionMode:r.z.enum(["same_session","sub_agent","background","notification","direct_report"]).default("background").describe("How to execute the hook"),timing:r.z.enum(["before","after"]).default("after").describe("When to fire relative to the event"),maxIterations:r.z.number().int().min(1).optional().describe("Maximum times to fire per session"),emitEvent:r.z.string().optional().describe("Custom event to emit on completion"),emitEventOnCondition:r.z.union([r.z.object({condition:r.z.object({field:r.z.string(),operator:r.z.enum(["contains","not_contains","equals","not_equals","matches","not_matches"]),value:r.z.string()}),event:r.z.string()}),r.z.array(r.z.object({condition:r.z.object({field:r.z.string(),operator:r.z.enum(["contains","not_contains","equals","not_equals","matches","not_matches"]),value:r.z.string()}),event:r.z.string()}))]).optional().describe("Conditional event emission based on output")}),exports.MetaWorkflowAddRecipeSchema=r.z.object({workflowId:r.z.string().describe("Workflow ID to add the recipe to"),recipeId:r.z.string().describe("Recipe ID to add"),position:r.z.number().int().min(0).optional().describe("Position in the workflow (0-based, appended if omitted)")}),exports.MetaWorkflowRemoveRecipeSchema=r.z.object({workflowId:r.z.string().describe("Workflow ID to remove the recipe from"),recipeId:r.z.string().describe("Recipe ID to remove")}),exports.MetaAgentListSchema=r.z.object({}),exports.MetaReferenceSchema=r.z.object({}),exports.TestingProcessListSchema=r.z.object({}),exports.TestingProcessGetSchema=r.z.object({processId:r.z.string().describe("Test process ID to retrieve")})
|
|
3378
3251
|
const l=r.z.object({name:r.z.string().min(1).describe('Command name (e.g., "Build", "Unit Tests")'),command:r.z.string().min(1).describe('Shell command to run (e.g., "npm test")'),required:r.z.boolean().default(!0).describe("If true, failure blocks the request (default: true)"),timeout:r.z.number().int().min(10).max(3600).default(300).describe("Max execution time in seconds (default: 300)")})
|
|
3379
|
-
exports.TestingProcessCreateSchema=r.z.object({name:r.z.string().min(1).describe("Name for the test process"),description:r.z.string().optional().describe("Description of what this process verifies"),scope:r.z.string().optional().describe('Path prefix for monorepo scoping (e.g., "packages/api/"). Omit for global.'),setup:r.z.array(r.z.string()).optional().describe('Commands to prepare the environment (e.g., ["ln -s ../../node_modules node_modules"])'),commands:r.z.array(l).min(1).describe("Test commands to execute in order"),verifyAcceptanceCriteria:r.z.boolean().optional().describe("When true, auto-tester verifies request acceptance criteria after running commands")}),exports.TestingProcessUpdateSchema=r.z.object({processId:r.z.string().describe("Test process ID to update"),name:r.z.string().min(1).optional().describe("New name"),description:r.z.string().optional().describe("New description"),scope:r.z.string().nullable().optional().describe("New scope (null to remove)"),isActive:r.z.boolean().optional().describe("Enable or disable the process"),setup:r.z.array(r.z.string()).optional().describe("New setup commands (replaces existing)"),commands:r.z.array(l).optional().describe("New test commands (replaces existing)"),verifyAcceptanceCriteria:r.z.boolean().optional().describe("When true, auto-tester verifies request acceptance criteria after running commands")}),exports.TestingReferenceSchema=r.z.object({}),exports.ExecuteTestCommandSchema=r.z.object({processId:r.z.string().describe("Test process ID containing the command"),commandName:r.z.string().describe('Name of the test command to run, or "setup" to run all setup commands in sequence')}),exports.ReportTestResultsSchema=r.z.object({status:r.z.enum(["passed","failed","error"]).describe("Overall result"),results:r.z.object({commands:r.z.array(r.z.object({name:r.z.string().describe("Command name"),status:r.z.enum(["passed","failed","skipped","error"]).describe("Command result"),output:r.z.string().optional().describe("Relevant output snippet"),diagnosis:r.z.string().optional().describe("Why it failed, if applicable")})).describe("Per-command results"),summary:r.z.string().describe("Brief overall summary"),acceptanceCriteria:r.z.array(r.z.object({criterion:r.z.string().describe("The acceptance criterion text"),status:r.z.enum(["verified","unverified","unclear"]),evidence:r.z.string().describe("How verified, or why not")})).optional().describe("AC verification results, if applicable")}).describe("Structured test results")}),exports.SessionMessageOperationsSchema=r.z.object({operation:r.z.enum(["send","reply","list","get","offer-handoff"]),type:r.z.enum(["question","report"]).optional().describe("Message type to send (required for send)"),toSessionId:r.z.string().optional().describe('Target session ID, or "parent" to auto-resolve to parent session (omit for broadcast questions)'),questionType:r.z.enum(["free-form","alternatives"]).optional().describe('Type of question (required for send type="question")'),questionContent:r.z.object({question:r.z.string().min(1).describe("The question text"),context:r.z.string().optional().describe("Additional context"),options:r.z.array(r.z.object({id:r.z.string(),label:r.z.string(),description:r.z.string().optional()})).optional().describe("Options for alternatives questions"),allowMultiple:r.z.boolean().optional().describe("Allow selecting multiple options")}).optional().describe('Question content (required for send type="question")'),priority:r.z.enum(["low","normal","high"]).optional().describe("Question priority"),expiresInHours:r.z.number().optional().describe("Question expiry in hours"),status:r.z.enum(["success","partial","failure","blocked"]).optional().describe('Report status (required for send type="report")'),summary:r.z.string().optional().describe('Report summary (required for send type="report")'),details:r.z.string().optional().describe("Report details"),finish:r.z.boolean().optional().describe("Release request associations after report"),messageCode:r.z.string().optional().describe("Message code (required for reply and get operations)"),respondedBySessionId:r.z.string().optional().describe("Session ID answering the question"),text:r.z.string().optional().describe("Text answer for free-form questions"),selectedOptions:r.z.array(r.z.string()).optional().describe("Selected option IDs for alternatives"),notes:r.z.string().optional().describe("Additional notes"),list:r.z.object({sessionId:r.z.string().optional().describe("Filter by session ID (auto-discovered if omitted)"),messageType:r.z.enum(["question","report","all"]).default("all").describe("Filter by message type"),direction:r.z.enum(["incoming","outgoing","all"]).default("all"),status:r.z.enum(["pending","answered","expired","success","partial","failure","blocked","all"]).default("all").describe("Filter by status"),readStatus:r.z.enum(["unread","read","acknowledged","all"]).default("all").describe("Filter by read status (reports only)"),limit:r.z.number().min(1).max(100).default(50),offset:r.z.number().min(0).default(0)}).optional().describe('List filters (operation: "list" only)'),offerHandoff:r.z.object({summary:r.z.string().describe("Summary of what was planned/created"),requestIds:r.z.array(r.z.string()).describe("Request IDs that were created from the plan")}).optional().describe('Handoff offer details (operation: "offer-handoff" only)')}).refine((e=>"send"===e.operation?!!e.type:"reply"===e.operation?!!e.messageCode:"list"===e.operation||("get"===e.operation?!!e.messageCode:"offer-handoff"===e.operation)),{message:"Invalid operation data: send requires type, reply requires messageCode, get requires messageCode"})},6252(e,exports,t){"use strict"
|
|
3252
|
+
exports.TestingProcessCreateSchema=r.z.object({name:r.z.string().min(1).describe("Name for the test process"),description:r.z.string().optional().describe("Description of what this process verifies"),scope:r.z.string().optional().describe('Path prefix for monorepo scoping (e.g., "packages/api/"). Omit for global.'),setup:r.z.array(r.z.string()).optional().describe('Commands to prepare the environment (e.g., ["ln -s ../../node_modules node_modules"])'),commands:r.z.array(l).min(1).describe("Test commands to execute in order"),verifyAcceptanceCriteria:r.z.boolean().optional().describe("When true, auto-tester verifies request acceptance criteria after running commands")}),exports.TestingProcessUpdateSchema=r.z.object({processId:r.z.string().describe("Test process ID to update"),name:r.z.string().min(1).optional().describe("New name"),description:r.z.string().optional().describe("New description"),scope:r.z.string().nullable().optional().describe("New scope (null to remove)"),isActive:r.z.boolean().optional().describe("Enable or disable the process"),setup:r.z.array(r.z.string()).optional().describe("New setup commands (replaces existing)"),commands:r.z.array(l).optional().describe("New test commands (replaces existing)"),verifyAcceptanceCriteria:r.z.boolean().optional().describe("When true, auto-tester verifies request acceptance criteria after running commands")}),exports.TestingReferenceSchema=r.z.object({}),exports.ExecuteTestCommandSchema=r.z.object({processId:r.z.string().describe("Test process ID containing the command"),commandName:r.z.string().describe('Name of the test command to run, or "setup" to run all setup commands in sequence')}),exports.ReportTestResultsSchema=r.z.object({status:r.z.enum(["passed","failed","error"]).describe("Overall result"),results:r.z.object({commands:r.z.array(r.z.object({name:r.z.string().describe("Command name"),status:r.z.enum(["passed","failed","skipped","error"]).describe("Command result"),output:r.z.string().optional().describe("Relevant output snippet"),diagnosis:r.z.string().optional().describe("Why it failed, if applicable")})).describe("Per-command results"),summary:r.z.string().describe("Brief overall summary"),acceptanceCriteria:r.z.array(r.z.object({criterion:r.z.string().describe("The acceptance criterion text"),status:r.z.enum(["verified","unverified","unclear"]),evidence:r.z.string().describe("How verified, or why not")})).optional().describe("AC verification results, if applicable")}).describe("Structured test results")}),exports.SessionMessageOperationsSchema=r.z.object({operation:r.z.enum(["send","reply","list","get","offer-handoff"]),type:r.z.enum(["question","report"]).optional().describe("Message type to send (required for send)"),toSessionId:r.z.string().optional().describe('Target session ID, or "parent" to auto-resolve to parent session (omit for broadcast questions)'),questionType:r.z.enum(["free-form","alternatives"]).optional().describe('Type of question (required for send type="question")'),questionContent:r.z.object({question:r.z.string().min(1).describe("The question text"),context:r.z.string().optional().describe("Additional context"),options:r.z.array(r.z.object({id:r.z.string(),label:r.z.string(),description:r.z.string().optional()})).optional().describe("Options for alternatives questions"),allowMultiple:r.z.boolean().optional().describe("Allow selecting multiple options")}).optional().describe('Question content (required for send type="question")'),priority:r.z.enum(["low","normal","high"]).optional().describe("Question priority"),expiresInHours:r.z.number().optional().describe("Question expiry in hours"),status:r.z.enum(["success","partial","failure","blocked"]).optional().describe('Report status (required for send type="report")'),summary:r.z.string().optional().describe('Report summary (required for send type="report")'),details:r.z.string().optional().describe("Report details"),finish:r.z.boolean().optional().describe("Release request associations after report"),messageCode:r.z.string().optional().describe("Message code (required for reply and get operations)"),respondedBySessionId:r.z.string().optional().describe("Session ID answering the question"),text:r.z.string().optional().describe("Text answer for free-form questions"),selectedOptions:r.z.array(r.z.string()).optional().describe("Selected option IDs for alternatives"),notes:r.z.string().optional().describe("Additional notes"),list:r.z.object({sessionId:r.z.string().optional().describe("Filter by session ID (auto-discovered if omitted)"),messageType:r.z.enum(["question","report","all"]).default("all").describe("Filter by message type"),direction:r.z.enum(["incoming","outgoing","all"]).default("all"),status:r.z.enum(["pending","answered","expired","success","partial","failure","blocked","all"]).default("all").describe("Filter by status"),readStatus:r.z.enum(["unread","read","acknowledged","all"]).default("all").describe("Filter by read status (reports only)"),limit:r.z.number().min(1).max(100).default(50),offset:r.z.number().min(0).default(0)}).optional().describe('List filters (operation: "list" only)'),offerHandoff:r.z.object({summary:r.z.string().describe("Summary of what was planned/created"),requestIds:r.z.array(r.z.string()).describe("Request IDs that were created from the plan")}).optional().describe('Handoff offer details (operation: "offer-handoff" only)')}).refine((e=>"send"===e.operation?!!e.type:"reply"===e.operation?!!e.messageCode:"list"===e.operation||("get"===e.operation?!!e.messageCode:"offer-handoff"===e.operation)),{message:"Invalid operation data: send requires type, reply requires messageCode, get requires messageCode"}),exports.UpdateSpecializationSchema=r.z.object({specialization:r.z.string().min(1).max(500).describe("Your updated specialization summary \u2014 a concise description of your accumulated domain expertise")})},6252(e,exports,t){"use strict"
|
|
3380
3253
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.def=void 0
|
|
3381
3254
|
const r=t(6183),n=t(405)
|
|
3382
3255
|
exports.def={name:"plan_write",description:"Modify project plans.\n\nOperations:\n\u2022 update - Update plan content\n\u2022 append - Append content to an existing plan\n\u2022 replace - Find and replace text within a plan\n\u2022 create-snapshot - Create a version snapshot\n\u2022 restore - Restore to a previous version",schema:r.PlanWriteSchema,annotations:{title:"Plan Write",readOnlyHint:!1,destructiveHint:!1},handler(e,t){return(0,n.handlePlanWrite)(e,t.context,t.apiClient,t.logger,t.metrics,t.mcpServer,t.cliOrigin)}}},6261(module){"use strict"
|
|
@@ -3513,24 +3386,24 @@ const q=_.filter((e=>e.path)),S=_.filter((e=>e.documentId))
|
|
|
3513
3386
|
y.info("Operation breakdown",{fileOperations:q.length,documentOperations:S.length})
|
|
3514
3387
|
const T=[]
|
|
3515
3388
|
for(const e of q){const{normalizedPath:r,fullPath:n}=u.validateAndNormalizePath(e.path,t)
|
|
3516
|
-
T.push({type:"file",path:r,fullPath:n,insertions:e.insertions})}const
|
|
3389
|
+
T.push({type:"file",path:r,fullPath:n,insertions:e.insertions})}const R=[]
|
|
3517
3390
|
if(S.length>0&&!t.documentFileManager)throw Error("Document file manager not available - cannot process document operations")
|
|
3518
|
-
for(const e of S)
|
|
3519
|
-
if(
|
|
3391
|
+
for(const e of S)R.push({type:"document",documentId:e.documentId,insertions:e.insertions})
|
|
3392
|
+
if(R.length>0&&t.apiClient){const e=R.map((e=>e.documentId))
|
|
3520
3393
|
try{await(0,p.ensureDocumentsNotLocked)(e,t.apiClient,y,a,"insert-lines-documents")}catch(e){if(e instanceof d.ValidationError)return{content:[{type:"text",text:e.message}],isError:!0}
|
|
3521
3394
|
throw e}}I=u.FileOperationPhase.TASK_VALIDATION,a.incrementCounter("insert_lines_phase",1,{phase:I})
|
|
3522
|
-
const
|
|
3523
|
-
let
|
|
3524
|
-
T.length>0&&x&&(
|
|
3525
|
-
let
|
|
3526
|
-
T.length>0&&x&&
|
|
3527
|
-
const $=await u.ensureCorrectWorkspaceContext({taskPromoted:
|
|
3395
|
+
const P=T.length>0?T[0].path:"document-operation",M=await u.validateTaskId(C,P,n,y,a,v.metricsPrefix),x=M?.requestId
|
|
3396
|
+
let j=null
|
|
3397
|
+
T.length>0&&x&&(j=await u.validateWorkItemStates(C,T[0].path,n,s,t,y,a,v.metricsPrefix))
|
|
3398
|
+
let O={taskPromoted:!1,requestPromoted:!1}
|
|
3399
|
+
T.length>0&&x&&j&&(O=await u.autoPromoteTaskStatus(C,M.status,x,j.request?.status,T[0].path,n,s,y,a,v.metricsPrefix),O.taskPromoted&&y.info("Auto-promoted task to in_progress for insert-lines operation",{taskId:C,requestId:x,previousStatus:M.status,newStatus:O.newTaskStatus,triggeringOperation:"insert-lines"}))
|
|
3400
|
+
const $=await u.ensureCorrectWorkspaceContext({taskPromoted:O.taskPromoted,requestId:x,context:t,operation:"insert-lines",logger:y,metrics:a,metricsPrefix:v.metricsPrefix})
|
|
3528
3401
|
if(!$.success){if($.isLockConflict)return{content:[{type:"text",text:"\u274c "+$.error}],isError:!0}
|
|
3529
3402
|
throw Error($.error)}if(T.length>0){y.debug("Re-validating file paths with correct workspace context",{operationCount:T.length,workspaceBasePath:t.workspaceManager?.getCurrentContext().basePath})
|
|
3530
3403
|
for(let e=0;e<T.length;e++){const r=T[e],n=q[e],{normalizedPath:o,fullPath:s}=u.validateAndNormalizePath(n.path,t)
|
|
3531
|
-
T[e]={...r,path:o,fullPath:s}}}if(
|
|
3404
|
+
T[e]={...r,path:o,fullPath:s}}}if(R.length>0&&x)try{await(0,h.validateRequestStatusForDocumentOperation)(x,s,y,a,"insert-lines-document")}catch(e){if(e instanceof d.ValidationError)return{content:[{type:"text",text:e.message}],isError:!0}
|
|
3532
3405
|
throw e}I=u.FileOperationPhase.RECORD_CREATION,a.incrementCounter("insert_lines_phase",1,{phase:I})
|
|
3533
|
-
const D=[...T.map((e=>({type:"file",path:e.path,insertions:e.insertions}))),...
|
|
3406
|
+
const D=[...T.map((e=>({type:"file",path:e.path,insertions:e.insertions}))),...R.map((e=>({type:"document",documentId:e.documentId,insertions:e.insertions})))],{toolRecordId:A}=await u.createFileOperationRecords(C,x,t.projectId,v.recordType,P,{operationCount:_.length,fileOperations:T.length,documentOperations:R.length,operations:D,userComment:E},n,o,y,a,v.metricsPrefix,m)
|
|
3534
3407
|
if(k=A,b=A,I=v.fileOperationPhase,a.incrementCounter("insert_lines_phase",1,{phase:I}),T.length>0&&t.git)try{y.debug("[INSERT-LINES] Checking for user changes before insert operations")
|
|
3535
3408
|
const e=await(0,g.commitUserChangesBeforeToolOperation)(t.git,"insert-lines",{requestId:x,taskId:C,workspaceManager:t.workspaceManager},y,a)
|
|
3536
3409
|
e.userChangesCommitted&&(y.debug("[INSERT-LINES] User changes committed before insert operations",{commitHash:e.commitHash?.substring(0,8),filesCommitted:e.filesCommitted}),y.info("User changes committed before insert-lines operation",{taskId:C,fileOperationsCount:T.length,userCommitHash:e.commitHash?.substring(0,8),userFilesCommitted:e.filesCommitted}))}catch(e){y.debug("[INSERT-LINES] Pre-tool commit failed, continuing with insertions",{error:e instanceof Error?e.message:e+""}),y.warn("Pre-tool user changes commit failed, continuing with insert operation",{taskId:C,fileOperationsCount:T.length,error:e instanceof Error?e.message:e+""})}y.debug("[INSERT-LINES] Proceeding with file operations",{fileCount:T.length})
|
|
@@ -3539,22 +3412,22 @@ let N=0,L=0,z=0
|
|
|
3539
3412
|
for(const e of T){const t={type:"file",path:e.path,success:!1,insertions:[],successfulInsertions:0,failedInsertions:0,totalLinesAdded:0}
|
|
3540
3413
|
try{if(await c.default.access(e.fullPath),!(await c.default.stat(e.fullPath)).isFile())throw Error("Path is not a file: "+e.path)
|
|
3541
3414
|
const n=await c.default.readFile(e.fullPath,"utf8"),{newContent:o,results:s}=await r(n,e.insertions)
|
|
3542
|
-
t.insertions=s,t.successfulInsertions=s.filter((e=>e.success)).length,t.failedInsertions=s.filter((e=>!e.success)).length,t.totalLinesAdded=s.filter((e=>e.success)).reduce(((e,t)=>e+(t.linesAdded||0)),0),o!==n&&t.successfulInsertions>0?(await c.default.writeFile(e.fullPath,o,"utf8"),t.success=!0,z++,y.info("File updated successfully",{path:e.path,successfulInsertions:t.successfulInsertions,failedInsertions:t.failedInsertions,linesAdded:t.totalLinesAdded})):0===t.failedInsertions&&(t.success=!0),N+=t.failedInsertions,L+=t.totalLinesAdded}catch(r){t.error=(0,f.getErrorMessage)(r),t.failedInsertions=e.insertions.length,N+=t.failedInsertions,y.error("File operation failed",{path:e.path,error:t.error})}F.push(t)}for(const e of
|
|
3415
|
+
t.insertions=s,t.successfulInsertions=s.filter((e=>e.success)).length,t.failedInsertions=s.filter((e=>!e.success)).length,t.totalLinesAdded=s.filter((e=>e.success)).reduce(((e,t)=>e+(t.linesAdded||0)),0),o!==n&&t.successfulInsertions>0?(await c.default.writeFile(e.fullPath,o,"utf8"),t.success=!0,z++,y.info("File updated successfully",{path:e.path,successfulInsertions:t.successfulInsertions,failedInsertions:t.failedInsertions,linesAdded:t.totalLinesAdded})):0===t.failedInsertions&&(t.success=!0),N+=t.failedInsertions,L+=t.totalLinesAdded}catch(r){t.error=(0,f.getErrorMessage)(r),t.failedInsertions=e.insertions.length,N+=t.failedInsertions,y.error("File operation failed",{path:e.path,error:t.error})}F.push(t)}for(const e of R){const n={type:"document",documentId:e.documentId,success:!1,insertions:[],successfulInsertions:0,failedInsertions:0,totalLinesAdded:0}
|
|
3543
3416
|
try{const o=await t.documentFileManager.getDocumentAsFile(e.documentId),s=t.documentFileManager.getCachedDocumentInfo(e.documentId)
|
|
3544
3417
|
n.filename=s?.filename
|
|
3545
3418
|
const i=await c.default.readFile(o,"utf8"),{newContent:a,results:l}=await r(i,e.insertions)
|
|
3546
|
-
n.insertions=l,n.successfulInsertions=l.filter((e=>e.success)).length,n.failedInsertions=l.filter((e=>!e.success)).length,n.totalLinesAdded=l.filter((e=>e.success)).reduce(((e,t)=>e+(t.linesAdded||0)),0),a!==i&&n.successfulInsertions>0?(await c.default.writeFile(o,a,"utf8"),t.documentFileManager.markForSync(e.documentId),n.success=!0,z++,y.info("Document updated successfully",{documentId:e.documentId,filename:n.filename,successfulInsertions:n.successfulInsertions,failedInsertions:n.failedInsertions,linesAdded:n.totalLinesAdded})):0===n.failedInsertions&&(n.success=!0),N+=n.failedInsertions,L+=n.totalLinesAdded}catch(t){n.error=(0,f.getErrorMessage)(t),n.failedInsertions=e.insertions.length,N+=n.failedInsertions,y.error("Document operation failed",{documentId:e.documentId,error:n.error})}F.push(n)}if(
|
|
3547
|
-
r?.success&&await t.documentFileManager.syncDocument(e.documentId)}}catch(e){y.warn("Some documents may not have synced properly",{error:e})}const B=await u.handleMultiFileGitCommit(C,T,F,z,{operationType:"Insert lines",toolRecordId:b,successField:"successfulInsertions",logger:y,metrics:a,metricsPrefix:"insert_lines"},t),H=u.processMultiFileOperationResults(F,"successfulInsertions"),{successfulOperations:U,failedOperations:
|
|
3548
|
-
try{await o.updateToolRecord(b,{metadata:{path:T.length>0?T[0].path:"document:"+
|
|
3549
|
-
if(t.workspaceManager&&(Y+=`**Branch:** \`${t.workspaceManager.getCurrentContext().branchName}\`\n\n`),Y+="**Summary:**\n",Y+=`- **Files processed:** ${U+
|
|
3419
|
+
n.insertions=l,n.successfulInsertions=l.filter((e=>e.success)).length,n.failedInsertions=l.filter((e=>!e.success)).length,n.totalLinesAdded=l.filter((e=>e.success)).reduce(((e,t)=>e+(t.linesAdded||0)),0),a!==i&&n.successfulInsertions>0?(await c.default.writeFile(o,a,"utf8"),t.documentFileManager.markForSync(e.documentId),n.success=!0,z++,y.info("Document updated successfully",{documentId:e.documentId,filename:n.filename,successfulInsertions:n.successfulInsertions,failedInsertions:n.failedInsertions,linesAdded:n.totalLinesAdded})):0===n.failedInsertions&&(n.success=!0),N+=n.failedInsertions,L+=n.totalLinesAdded}catch(t){n.error=(0,f.getErrorMessage)(t),n.failedInsertions=e.insertions.length,N+=n.failedInsertions,y.error("Document operation failed",{documentId:e.documentId,error:n.error})}F.push(n)}if(R.length>0)try{for(const e of R){const r=F.find((t=>t.documentId===e.documentId))
|
|
3420
|
+
r?.success&&await t.documentFileManager.syncDocument(e.documentId)}}catch(e){y.warn("Some documents may not have synced properly",{error:e})}const B=await u.handleMultiFileGitCommit(C,T,F,z,{operationType:"Insert lines",toolRecordId:b,successField:"successfulInsertions",logger:y,metrics:a,metricsPrefix:"insert_lines"},t),H=u.processMultiFileOperationResults(F,"successfulInsertions"),{successfulOperations:U,failedOperations:G,totalSuccessfulChanges:W,overallSuccess:V,successfulFiles:J,failedFiles:K}=H
|
|
3421
|
+
try{await o.updateToolRecord(b,{metadata:{path:T.length>0?T[0].path:"document:"+R[0]?.documentId,status:V?"completed":"failed",error:V?void 0:G+" operations failed",totalOperations:F.length,successfulFiles:J,failedFiles:K,operations:D,totalSuccessfulInsertions:W,totalFailedInsertions:N,totalLinesAdded:L,operationsWithChanges:z,processingTime:Date.now()-w,userComment:E,...T.length>0&&B.success&&B.commitHash&&{commitHash:B.commitHash,previousCommitHash:B.previousCommitHash||void 0}},note:V?`Line insertion completed: ${U}/${F.length} operations successful${T.length>0?" (committed to git)":""}`:`Line insertion partially failed: ${G}/${F.length} operations failed`})}catch(e){y.warn("Failed to update tool record",{recordError:e})}let Y="## Line Insertion Results\n\n"
|
|
3422
|
+
if(t.workspaceManager&&(Y+=`**Branch:** \`${t.workspaceManager.getCurrentContext().branchName}\`\n\n`),Y+="**Summary:**\n",Y+=`- **Files processed:** ${U+G}\n`,Y+=`- **Successful operations:** ${U}\n`,Y+=`- **Failed operations:** ${G}\n`,Y+=`- **Total insertions:** ${W} successful, ${N} failed\n`,Y+=`- **Total Lines Added:** ${L}\n`,Y+="\n",B.success&&B.commitHash&&(Y+="**Git Commit:**\n",Y+=`- **Commit Hash:** ${B.commitHash.substring(0,8)}\n`,Y+=`- **Files Committed:** ${B.filesCommitted.length}\n`,B.previousCommitHash&&(Y+=`- **Previous Commit:** ${B.previousCommitHash.substring(0,8)}\n`),Y+="\n"),$.lockAcquired&&$.lockedRequestId&&(Y+=`\u{1f512} **Locked request:** ${$.lockedRequestId}\n\n`),1===F.length){const e=F[0]
|
|
3550
3423
|
if(Y+=`**Operation:** ${e.success?"\u2705 Success":"\u274c Failed"}\n`,"file"===e.type?Y+=`**File:** ${e.path}\n`:(Y+="**Document:** "+e.documentId,e.filename&&(Y+=` (${e.filename})`),Y+="\n"),e.error?Y+=`**Error:** ${e.error}\n`:(Y+=`**Insertions:** ${e.successfulInsertions} successful`,e.failedInsertions>0&&(Y+=`, ${e.failedInsertions} failed`),Y+="\n",Y+=`**Lines Added:** ${e.totalLinesAdded}\n`),e.insertions.some((e=>!e.success))){Y+="**Failed Insertion Details:**\n"
|
|
3551
3424
|
for(const t of e.insertions.filter((e=>!e.success))){const e="between"===t.type?`between lines ${t.afterLine} and ${t.beforeLine}`:`${t.type} line ${t.line}`
|
|
3552
|
-
Y+=`- ${t.type} insertion ${e}: ${t.error}\n`}}}else{Y+="**Summary:**\n",Y+=`- **Total Operations:** ${F.length}\n`,Y+=`- **Successful:** ${U}\n`,Y+=`- **Failed:** ${
|
|
3425
|
+
Y+=`- ${t.type} insertion ${e}: ${t.error}\n`}}}else{Y+="**Summary:**\n",Y+=`- **Total Operations:** ${F.length}\n`,Y+=`- **Successful:** ${U}\n`,Y+=`- **Failed:** ${G}\n`,Y+=`- **Total Insertions:** ${W} successful, ${N} failed\n`,Y+=`- **Total Lines Added:** ${L}\n\n`,Y+="**Detailed Results:**\n\n"
|
|
3553
3426
|
for(const e of F){if("file"===e.type?Y+=`### File: ${e.path}\n`:(Y+="### Document: "+e.documentId,e.filename&&(Y+=` (${e.filename})`),Y+="\n"),Y+=`- **Status:** ${e.success?"\u2705 Success":"\u274c Failed"}\n`,e.error?Y+=`- **Error:** ${e.error}\n`:(Y+=`- **Insertions:** ${e.successfulInsertions} successful`,e.failedInsertions>0&&(Y+=`, ${e.failedInsertions} failed`),Y+="\n",Y+=`- **Lines Added:** ${e.totalLinesAdded}\n`),e.insertions.some((e=>!e.success))){Y+="- **Failed Insertion Details:**\n"
|
|
3554
3427
|
for(const t of e.insertions.filter((e=>!e.success))){const e="between"===t.type?`between lines ${t.afterLine} and ${t.beforeLine}`:`${t.type} line ${t.line}`
|
|
3555
|
-
Y+=` - ${t.type} insertion ${e}: ${t.error}\n`}}Y+="\n"}}
|
|
3428
|
+
Y+=` - ${t.type} insertion ${e}: ${t.error}\n`}}Y+="\n"}}R.length>0&&(Y+="\u{1f4c4} **Document Changes:** Modified documents have been automatically synced back to the tracking system.\n\n")
|
|
3556
3429
|
const Q=Date.now()-w
|
|
3557
|
-
return y.info("Insert lines operation completed",{duration:Q,success:V,totalOperations:F.length,successfulOperations:U,failedOperations:
|
|
3430
|
+
return y.info("Insert lines operation completed",{duration:Q,success:V,totalOperations:F.length,successfulOperations:U,failedOperations:G}),a.incrementCounter("insert_lines_total",1,{success:V}),{content:[{type:"text",text:Y}],isError:!V}}catch(t){const r=Date.now()-w
|
|
3558
3431
|
if(y.error("Insert lines operation failed",{error:t instanceof Error?t.stack:t+"",duration:r,phase:I}),b)try{await o.updateToolRecord(b,{metadata:{path:e?.operations?.[0]?.path||e?.operations?.[0]?.documentId,status:"failed",error:(0,f.getErrorMessage)(t),phase:I,duration:r,userComment:e?.comment},note:"Line insertion failed: "+(0,f.getErrorMessage)(t)})}catch(e){}return a.incrementCounter("insert_lines_errors",1,{phase:I}),{content:[{type:"text",text:"\u274c **Insert Lines Failed:** "+(0,f.getErrorMessage)(t)}],isError:!0}}}
|
|
3559
3432
|
const c=a(t(1943)),l=t(6183),u=i(t(5967)),d=t(9860),h=t(5003),g=t(7478),p=t(9949),f=t(8824),m=t(3255)},6539(e,exports,t){"use strict"
|
|
3560
3433
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.ClientFactory=void 0
|
|
@@ -3572,54 +3445,53 @@ const S=new d.RequestClient(e,m,y,_,v||void 0,C,{timeout:w.timeout,retryAttempts
|
|
|
3572
3445
|
b.registerClient(S),m.info("RequestClient post-constructor token: "+(S.getAuthToken()?"present":"missing"))
|
|
3573
3446
|
const T=new g.DocumentClient(e,m,y,_,v||void 0,C,{timeout:w.timeout,retryAttempts:w.retryAttempts,retryDelay:w.retryDelay,circuitBreakerThreshold:w.circuitBreakerThreshold,circuitBreakerResetTime:w.circuitBreakerResetTime})
|
|
3574
3447
|
b.registerClient(T)
|
|
3575
|
-
const
|
|
3576
|
-
b.registerClient(
|
|
3577
|
-
const
|
|
3578
|
-
if(b.registerClient(
|
|
3448
|
+
const R=new f.ToolRecordClient(e,m,y,_,v||void 0,C,{timeout:w.timeout,retryAttempts:w.retryAttempts,retryDelay:w.retryDelay,circuitBreakerThreshold:w.circuitBreakerThreshold,circuitBreakerResetTime:w.circuitBreakerResetTime})
|
|
3449
|
+
b.registerClient(R)
|
|
3450
|
+
const P=new u.ProxyClient(e,m,y,_,v||void 0,C,{timeout:w.timeout,retryAttempts:w.retryAttempts,retryDelay:w.retryDelay,circuitBreakerThreshold:w.circuitBreakerThreshold,circuitBreakerResetTime:w.circuitBreakerResetTime})
|
|
3451
|
+
if(b.registerClient(P),!w.alchemyPath)throw Error("alchemyPath is required for ProjectSynchronizer creation. Cannot create API client without project synchronization capabilities.")
|
|
3579
3452
|
try{m.info("Creating ProjectSynchronizer components")
|
|
3580
3453
|
const{ProjectRegistry,ProjectFileSystem,ProjectSynchronizer}=await t.e(478).then(t.bind(t,5478)),e=new ProjectRegistry(m),r=new ProjectFileSystem(m),n=new ProjectSynchronizer(m,e,new l.ProjectClientAdapter(_,m),r,{createRemoteProjects:!0})
|
|
3581
3454
|
_.setProjectSynchronizer(n),m.info("ProjectSynchronizer created and connected to ProjectClient")}catch(e){const t="Failed to create required ProjectSynchronizer components: "+(0,h.getErrorMessage)(e)
|
|
3582
|
-
throw m.error(t,{error:e instanceof Error?e.stack:e+""}),Error(t)}const
|
|
3583
|
-
m.info("API client initialized with specialized clients"),v?(
|
|
3455
|
+
throw m.error(t,{error:e instanceof Error?e.stack:e+""}),Error(t)}const M=new o.ApiClient(I,_,E,q,S,T,R,P,m)
|
|
3456
|
+
m.info("API client initialized with specialized clients"),v?(M.setAuthToken(v),m.info("Auth token set on ApiClient during creation",{hasToken:!0,tokenLength:v.length})):m.warn("No auth token available during ApiClient creation",{info:"Client will need to authenticate before making requests"})
|
|
3584
3457
|
const x=b.verifyAllClients()
|
|
3585
3458
|
x.success?m.info("Token consistency verified across all clients"):m.error(`Token inconsistency detected in ${x.failedClients.length} clients: ${x.failedClients.join(", ")}`)
|
|
3586
|
-
const
|
|
3587
|
-
return v&&!
|
|
3459
|
+
const j=M.getAuthToken()
|
|
3460
|
+
return v&&!j?(m.error("CRITICAL: ApiClient token was not set properly!"),M.setAuthToken(v)):j&&m.info("ApiClient token verified",{tokenLength:j.length,matches:j===v}),m.info("API client creation completed successfully"),M}}},6540(e,exports){"use strict"
|
|
3588
3461
|
var t
|
|
3589
3462
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.LogLevel=void 0,function(e){e.ERROR="error",e.WARN="warn",e.INFO="info",e.DEBUG="debug"}(t||(exports.LogLevel=t={}))},6552(e,exports,t){"use strict"
|
|
3590
|
-
async function r(){const e=new o.StdioServerTransport,t=(0,l.setupParentProcessDetection)((()=>{
|
|
3591
|
-
if(
|
|
3592
|
-
throw
|
|
3463
|
+
async function r(){const e=new o.StdioServerTransport,t=(0,l.setupParentProcessDetection)((()=>{k.info("Parent process gone or orphan detected. Shutting down."),process.exit(0)}))
|
|
3464
|
+
if(_)try{await _.connectStdio(),(0,a.isDebugToolsEnabled)()&&k.info("Connected stdio transport to server")}catch(e){const t=e instanceof Error?{message:e.message,name:e.name,stack:e.stack}:e+""
|
|
3465
|
+
throw k.error("Failed to connect stdio transport",{errorDetails:t}),e}else k.error("No global server instance available to connect transport")
|
|
3593
3466
|
return{transport:e,shutdownHandler:t}}var n=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}}
|
|
3594
3467
|
Object.defineProperty(exports,"__esModule",{value:!0})
|
|
3595
|
-
const o=t(5802),s=n(t(6928)),i=t(184),a=t(3444),c=t(1152),l=t(8851),u=t(8411),d=n(t(9896)),h=t(4139),g=t(
|
|
3596
|
-
console.error("\n=== MCP STARTUP DIAGNOSTICS ==="),console.error("Script path (process.argv[1]):",process.argv[1]),console.error("Base directory:",
|
|
3597
|
-
const
|
|
3598
|
-
const
|
|
3599
|
-
process.stdout.write=function(e,t,r){try{if("string"==typeof e)try{JSON.parse(e)}catch(t){return e.includes('"__message_type"')||(process.stderr.write("[STDOUT REDIRECTED]: "+e),r&&r()),!0}return"string"==typeof t&&"function"==typeof r?
|
|
3600
|
-
try{if(d.default.existsSync(
|
|
3601
|
-
d.default.writeFileSync(e,(new Date).toISOString()),
|
|
3602
|
-
let
|
|
3603
|
-
const
|
|
3604
|
-
void 0===
|
|
3605
|
-
let
|
|
3606
|
-
|
|
3607
|
-
|
|
3608
|
-
|
|
3609
|
-
|
|
3610
|
-
|
|
3611
|
-
|
|
3612
|
-
|
|
3613
|
-
|
|
3614
|
-
|
|
3615
|
-
|
|
3616
|
-
e
|
|
3617
|
-
|
|
3618
|
-
E=e,global.__serverInitialized=!0,(0,a.isDebugToolsEnabled)()&&b.info("MCP server created successfully")
|
|
3468
|
+
const o=t(5802),s=n(t(6928)),i=t(184),a=t(3444),c=t(1152),l=t(8851),u=t(8411),d=n(t(9896)),h=t(4139),g=t(8824),p=t(9939),f=t(7960),m=process.argv.slice(2),y=m[0]||process.cwd(),w=s.default.resolve(y)
|
|
3469
|
+
console.error("\n=== MCP STARTUP DIAGNOSTICS ==="),console.error("Script path (process.argv[1]):",process.argv[1]),console.error("Base directory:",w),console.error("ENABLE_DEBUG_TOOLS env:",process.env.ENABLE_DEBUG_TOOLS),console.error("DEBUG_LOGGING env:",process.env.DEBUG_LOGGING),console.error("isDevBuild():",(0,f.isDevBuild)()),console.error("isDebugToolsEnabled():",(0,a.isDebugToolsEnabled)()),console.error("===============================\n")
|
|
3470
|
+
const k=(0,a.createEnvLogger)({serviceName:"direct-mcp-server",console:!0,baseDir:w});(0,a.isDebugToolsEnabled)()?k.info("MCP Direct server initializing",{baseDir:w,debugLogging:process.env.DEBUG_LOGGING,debugLevel:process.env.DEBUG_LEVEL,pid:process.pid}):k.info("MCP Direct server starting"),console.log=function(...e){console.error("[LOG]",...e)},console.info=function(...e){console.error("[INFO]",...e)},console.warn=function(...e){console.error("[WARN]",...e)},process.on("uncaughtException",(e=>{if(k.error("UNCAUGHT EXCEPTION: "+e,{stack:e.stack||"No stack available"}),_)try{_.cleanupSSEConnection()}catch(e){k.error("Error during cleanup after uncaught exception: "+e)}setTimeout((()=>process.exit(1)),500)})),process.on("unhandledRejection",(e=>{k.error("UNHANDLED REJECTION: "+e,{stack:e instanceof Error?e.stack:"No stack available"})})),process.on("exit",(e=>{k.info("Process exiting with code: "+e)}))
|
|
3471
|
+
const b=process.stdout.write
|
|
3472
|
+
process.stdout.write=function(e,t,r){try{if("string"==typeof e)try{JSON.parse(e)}catch(t){return e.includes('"__message_type"')||(process.stderr.write("[STDOUT REDIRECTED]: "+e),r&&r()),!0}return"string"==typeof t&&"function"==typeof r?b.call(process.stdout,e,t,r):"function"==typeof t?b.call(process.stdout,e,void 0,t):b.call(process.stdout,e)}catch(e){return process.stderr.write("[STDOUT ERROR]: "+e),!0}},(0,a.isDebugToolsEnabled)()&&(k.info("Initialized stdout filtering to ensure only valid JSON is sent"),k.info("!!!MARKER!!! COMMAND-LINE ARGS:",{args:JSON.stringify(m)}),k.info("!!!MARKER!!! BASE DIRECTORY:",{baseDir:y}),k.info("!!!MARKER!!! ABSOLUTE BASE DIR:",{absBaseDir:w}),k.info("Working with base directory:",{absBaseDir:w}))
|
|
3473
|
+
try{if(d.default.existsSync(w)||(k.warn(`Base directory ${w} does not exist. Creating it...`),d.default.mkdirSync(w,{recursive:!0})),(0,a.isDebugToolsEnabled)()){const e=s.default.join(w,".mcp-test-file")
|
|
3474
|
+
d.default.writeFileSync(e,(new Date).toISOString()),k.info("Successfully wrote test file to "+e),d.default.unlinkSync(e),k.info("Successfully deleted test file"),k.info(`Confirmed base directory ${w} exists and is accessible`)}}catch(e){k.error(`Error accessing base directory ${w}:`,{error:e}),k.warn("This may cause issues with file operations - please check permissions")}const I=(0,c.createMetricsCollector)(!1)
|
|
3475
|
+
let v=process.env.REMOTE_SERVER_URL||"https://api.alchemylabcode.com"
|
|
3476
|
+
const C=global.__serverInitialized
|
|
3477
|
+
void 0===C?(global.__serverInitialized=!1,(0,a.isDebugToolsEnabled)()&&k.info("FIRST RUN: Setting global.__serverInitialized to false")):(0,a.isDebugToolsEnabled)()&&k.info("REUSE: global.__serverInitialized is already "+global.__serverInitialized)
|
|
3478
|
+
let _=null
|
|
3479
|
+
try{(0,u.acquireProcessLock)(w)||(k.error(`Process lock acquisition failed for ${w}. Another instance may be running.`),k.error("This instance will exit to prevent duplicate initialization"),process.exit(1)),(0,a.isDebugToolsEnabled)()&&k.info("Multi-agent mode enabled - allowing concurrent access to "+w)}catch(e){k.error("Lock acquisition threw exception",{error:(0,g.getErrorMessage)(e),stack:e instanceof Error?e.stack:void 0}),process.exit(1)}(0,a.isDebugToolsEnabled)()&&(k.info("============================================================"),k.info(`PROCESS START: PID=${process.pid}, TIME=${(new Date).toISOString()}`),k.info("BASE DIR: "+w),k.info("ALCHEMY PATH: "+s.default.join(w,h.ALCHEMY_DIR_NAME)),k.info("PROJECT PATH: "+s.default.join(w,h.ALCHEMY_DIR_NAME+"/project.json")),k.info("MULTI-AGENT MODE: true"),k.info("MCP client information will be captured during protocol initialization")),k.info("Starting MCP server"),(0,a.isDebugToolsEnabled)()&&(k.info("============================================================"),k.info("Base directory: "+w),k.info("Remote server URL: "+v),k.info("Node version: "+process.version),k.info("Current working directory: "+process.cwd()),k.info("ALLOWED_DIRECTORIES env var: not used"),k.info("Server already initialized: "+(C?"YES":"NO"))),C&&((0,a.isDebugToolsEnabled)()&&(k.info("Server already initialized globally, reusing existing server instance"),k.info("Reconnecting stdio to existing server...")),r().catch((e=>{const t=e instanceof Error?{message:e.message,name:e.name,stack:e.stack}:e+""
|
|
3480
|
+
k.error("Failed to connect stdio transport to existing server",{errorDetails:t}),process.exit(1)})))
|
|
3481
|
+
try{const e=d.default.existsSync(w)
|
|
3482
|
+
if((0,a.isDebugToolsEnabled)()&&k.info("Base directory exists: "+e),e&&(0,a.isDebugToolsEnabled)()){const e=d.default.statSync(w)
|
|
3483
|
+
k.info(`Directory stats: isDirectory=${e.isDirectory()}, mode=${e.mode.toString(8)}`)}else(0,a.isDebugToolsEnabled)()&&k.info("Directory does not exist, trying to create it"),d.default.mkdirSync(w,{recursive:!0})}catch(e){k.error("Error checking directory: "+e)}if(!d.default.existsSync(w))try{d.default.mkdirSync(w,{recursive:!0}),(0,a.isDebugToolsEnabled)()&&k.info("Created base directory: "+w)}catch(e){k.error("Failed to create base directory: "+e)}const E=s.default.join(w,h.ALCHEMY_DIR_NAME)
|
|
3484
|
+
if(!d.default.existsSync(E))try{d.default.mkdirSync(E,{recursive:!0}),(0,a.isDebugToolsEnabled)()&&k.info("Created alchemy lab directory: "+E)}catch(e){k.error("Failed to create alchemy lab directory: "+e)}try{(async function(){try{v=await async function(){if(process.env.REMOTE_SERVER_URL)return process.env.REMOTE_SERVER_URL
|
|
3485
|
+
try{const{createConfigManager:e}=await Promise.resolve().then(t.t.bind(t,9060,23)),r=e(k),n=await r.getInstallationConfig()
|
|
3486
|
+
if(n.remoteServerUrl)return(0,a.isDebugToolsEnabled)()&&k.info("Loaded REMOTE_SERVER_URL from installation config",{remoteServerUrl:n.remoteServerUrl}),n.remoteServerUrl}catch(e){(0,a.isDebugToolsEnabled)()&&k.debug("Could not read REMOTE_SERVER_URL from installation config",{error:e instanceof Error?e.message:"Unknown error"})}return"https://api.alchemylabcode.com"}()
|
|
3487
|
+
try{const e=await(0,p.syncPlugins)(w,(0,f.isDevBuild)(),k)
|
|
3488
|
+
e.synced.length>0&&k.info("Synced plugins on startup",{synced:e.synced}),e.errors.length>0&&k.warn("Some plugins failed to sync",{errors:e.errors})}catch(e){k.warn("Plugin sync failed",{error:e instanceof Error?e.message:"Unknown error"})}(0,a.isDebugToolsEnabled)()&&(k.info("Creating MCP server with base dir: "+w),k.info("Using remote server URL: "+v))
|
|
3489
|
+
const e=await(0,i.createServer)(w,k,I,v)
|
|
3490
|
+
_=e,global.__serverInitialized=!0,(0,a.isDebugToolsEnabled)()&&k.info("MCP server created successfully")
|
|
3619
3491
|
const n=r()
|
|
3620
|
-
return(0,a.isDebugToolsEnabled)()&&
|
|
3621
|
-
|
|
3622
|
-
|
|
3492
|
+
return(0,a.isDebugToolsEnabled)()&&k.info("Stdio transport registered with server"),{server:_,transportInfo:n}}catch(e){throw k.error("Failed to initialize MCP server",{error:e}),e}})().then((()=>{(0,a.isDebugToolsEnabled)()&&k.info("MCP server initialization complete")})).catch((e=>{const t=e instanceof Error?{message:e.message,name:e.name,stack:e.stack}:e+""
|
|
3493
|
+
k.error("Server initialization failed",{errorDetails:t}),process.exit(1)}))}catch(e){const t=e instanceof Error?{message:e.message,name:e.name,stack:e.stack}:e+""
|
|
3494
|
+
k.error("Exception during server initialization",{errorDetails:t}),process.exit(1)}process.on("SIGTERM",(()=>{k.info("SIGTERM received, shutting down"),setTimeout((()=>process.exit(0)),500)})),process.on("SIGINT",(()=>{k.info("SIGINT received, shutting down"),setTimeout((()=>process.exit(0)),500)}))},6595(e,exports,t){"use strict"
|
|
3623
3495
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.ApiClient=void 0
|
|
3624
3496
|
const r=t(1599),n=t(2690),o=t(4465),s=t(5187),i=t(5674),a=t(8824)
|
|
3625
3497
|
exports.ApiClient=class{constructor(e,t,r,n,o,s,i,a,c){this.options={createRecords:!0},this.alchemyPath="",this.sessionRequestAssociationClient=null,this.sessionMessageClient=null,this.sessionTagMappingClient=null,this.cliSessionClient=null,this.logger=c,this.authManager=e,this.projectClient=t,this.taskClient=r,this.fileClient=n,this.requestClient=o,this.documentClient=s,this.toolRecordClient=i,this.proxyClient=a,this.tokenSynchronizer=e.getTokenSynchronizer(),this.baseUrl=a.baseUrl||"",this.documentClient&&"function"==typeof this.documentClient.setParentApiClient&&this.documentClient.setParentApiClient(this),this.logger.info("API client initialized with specialized clients")}async setToken(e){return this.authManager.setToken(e)}async getToken(){return this.authManager.getToken()}async hasValidToken(){return this.authManager.hasValidToken()}async removeToken(){return this.authManager.removeToken()}setOptions(e){this.options={...this.options,...e},this.logger.info("API client options updated",{options:this.options})}getOptions(){return{...this.options}}isOffline(){const e=this.projectClient.isOffline?.()||!1,t=this.fileClient.isOffline?.()||!1,r=this.proxyClient.isOffline?.()||!1,n=e||t||r
|
|
@@ -3664,48 +3536,48 @@ try{const i=u.validateArgs(e,l.ReplaceLinesSchema),{taskId:_,operations:E,commen
|
|
|
3664
3536
|
if(w.info("Replacing lines in files and documents",{taskId:_,operationCount:E.length,comment:q}),!E||0===E.length)throw new d.ValidationError("At least one operation is required")
|
|
3665
3537
|
const S=E.filter((e=>e.path)),T=E.filter((e=>e.documentId))
|
|
3666
3538
|
w.info("Operation breakdown",{fileOperations:S.length,documentOperations:T.length})
|
|
3667
|
-
const
|
|
3539
|
+
const R=[]
|
|
3668
3540
|
for(const e of S){const{normalizedPath:r,fullPath:n}=u.validateAndNormalizePath(e.path,t)
|
|
3669
|
-
|
|
3541
|
+
R.push({type:"file",path:r,fullPath:n,replacements:e.replacements.map((e=>({lines:(0,y.parseLineSpec)(e.lines),content:e.content})))})}const P=[]
|
|
3670
3542
|
if(T.length>0&&!t.documentFileManager)throw Error("Document file manager not available - cannot process document operations")
|
|
3671
|
-
for(const e of T)
|
|
3672
|
-
if(
|
|
3543
|
+
for(const e of T)P.push({type:"document",documentId:e.documentId,replacements:e.replacements.map((e=>({lines:(0,y.parseLineSpec)(e.lines),content:e.content})))})
|
|
3544
|
+
if(P.length>0&&t.apiClient){const e=P.map((e=>e.documentId))
|
|
3673
3545
|
try{await(0,p.ensureDocumentsNotLocked)(e,t.apiClient,w,a,"replace-lines-documents")}catch(e){if(e instanceof d.ValidationError)return{content:[{type:"text",text:e.message}],isError:!0}
|
|
3674
3546
|
throw e}}v=u.FileOperationPhase.TASK_VALIDATION,a.incrementCounter("replace_lines_phase",1,{phase:v})
|
|
3675
|
-
const
|
|
3676
|
-
let
|
|
3677
|
-
|
|
3547
|
+
const M=R.length>0?R[0].path:"document-operation",x=await u.validateTaskId(_,M,n,w,a,C.metricsPrefix),j=x?.requestId
|
|
3548
|
+
let O=null
|
|
3549
|
+
R.length>0&&j&&(O=await u.validateWorkItemStates(_,R[0].path,n,s,t,w,a,C.metricsPrefix))
|
|
3678
3550
|
let $={taskPromoted:!1,requestPromoted:!1}
|
|
3679
|
-
|
|
3680
|
-
const D=await u.ensureCorrectWorkspaceContext({taskPromoted:$.taskPromoted,requestId:
|
|
3551
|
+
R.length>0&&j&&O&&($=await u.autoPromoteTaskStatus(_,x.status,j,O.request?.status,R[0].path,n,s,w,a,C.metricsPrefix),$.taskPromoted&&w.info("Auto-promoted task to in_progress for replace-lines operation",{taskId:_,requestId:j,previousStatus:x.status,newStatus:$.newTaskStatus,triggeringOperation:"replace-lines"}))
|
|
3552
|
+
const D=await u.ensureCorrectWorkspaceContext({taskPromoted:$.taskPromoted,requestId:j,context:t,operation:"replace-lines",logger:w,metrics:a,metricsPrefix:C.metricsPrefix})
|
|
3681
3553
|
if(!D.success){if(D.isLockConflict)return{content:[{type:"text",text:"\u274c "+D.error}],isError:!0}
|
|
3682
|
-
throw Error(D.error)}if(
|
|
3683
|
-
for(let e=0;e<
|
|
3684
|
-
|
|
3554
|
+
throw Error(D.error)}if(R.length>0){w.debug("Re-validating file paths with correct workspace context",{operationCount:R.length,workspaceBasePath:t.workspaceManager?.getCurrentContext().basePath})
|
|
3555
|
+
for(let e=0;e<R.length;e++){const r=R[e],n=S[e],{normalizedPath:o,fullPath:s}=u.validateAndNormalizePath(n.path,t)
|
|
3556
|
+
R[e]={...r,path:o,fullPath:s}}}if(P.length>0&&j)try{await(0,h.validateRequestStatusForDocumentOperation)(j,s,w,a,"replace-lines-document")}catch(e){if(e instanceof d.ValidationError)return{content:[{type:"text",text:e.message}],isError:!0}
|
|
3685
3557
|
throw e}v=u.FileOperationPhase.RECORD_CREATION,a.incrementCounter("replace_lines_phase",1,{phase:v})
|
|
3686
|
-
const A=[...
|
|
3687
|
-
if(b=F,I=F,v=C.fileOperationPhase,a.incrementCounter("replace_lines_phase",1,{phase:v}),
|
|
3688
|
-
const e=await(0,g.commitUserChangesBeforeToolOperation)(t.git,"replace-lines",{requestId:
|
|
3689
|
-
e.userChangesCommitted&&(w.debug("[REPLACE-LINES] User changes committed before replace operations",{commitHash:e.commitHash?.substring(0,8),filesCommitted:e.filesCommitted}),w.info("User changes committed before replace-lines operation",{taskId:_,fileOperationsCount:
|
|
3558
|
+
const A=[...R.map((e=>({type:"file",path:e.path,replacements:e.replacements}))),...P.map((e=>({type:"document",documentId:e.documentId,replacements:e.replacements})))],{toolRecordId:F}=await u.createFileOperationRecords(_,j,t.projectId,C.recordType,M,{operationCount:E.length,fileOperations:R.length,documentOperations:P.length,operations:A,userComment:q},n,o,w,a,C.metricsPrefix,m)
|
|
3559
|
+
if(b=F,I=F,v=C.fileOperationPhase,a.incrementCounter("replace_lines_phase",1,{phase:v}),R.length>0&&t.git)try{w.debug("[REPLACE-LINES] Checking for user changes before replace operations")
|
|
3560
|
+
const e=await(0,g.commitUserChangesBeforeToolOperation)(t.git,"replace-lines",{requestId:j,taskId:_,workspaceManager:t.workspaceManager},w,a)
|
|
3561
|
+
e.userChangesCommitted&&(w.debug("[REPLACE-LINES] User changes committed before replace operations",{commitHash:e.commitHash?.substring(0,8),filesCommitted:e.filesCommitted}),w.info("User changes committed before replace-lines operation",{taskId:_,fileOperationsCount:R.length,userCommitHash:e.commitHash?.substring(0,8),userFilesCommitted:e.filesCommitted}))}catch(e){w.debug("[REPLACE-LINES] Pre-tool commit failed, continuing with replacements",{error:e instanceof Error?e.message:e+""}),w.warn("Pre-tool user changes commit failed, continuing with replace operation",{taskId:_,fileOperationsCount:R.length,error:e instanceof Error?e.message:e+""})}w.debug("[REPLACE-LINES] Proceeding with file operations",{fileCount:R.length})
|
|
3690
3562
|
const N=[]
|
|
3691
3563
|
let L=0,z=0,B=0,H=0
|
|
3692
|
-
for(const e of
|
|
3564
|
+
for(const e of R){const t={type:"file",path:e.path,success:!1,replacements:[],successfulReplacements:0,failedReplacements:0,totalLinesReplaced:0,totalLinesAdded:0}
|
|
3693
3565
|
try{if(await c.default.access(e.fullPath),!(await c.default.stat(e.fullPath)).isFile())throw Error("Path is not a file: "+e.path)
|
|
3694
3566
|
const n=await c.default.readFile(e.fullPath,"utf8"),{newContent:o,results:s}=await r(n,e.replacements)
|
|
3695
|
-
t.replacements=s,t.successfulReplacements=s.filter((e=>e.success)).length,t.failedReplacements=s.filter((e=>!e.success)).length,t.totalLinesReplaced=s.filter((e=>e.success)).reduce(((e,t)=>e+(t.linesReplaced||0)),0),t.totalLinesAdded=s.filter((e=>e.success)).reduce(((e,t)=>e+(t.linesAdded||0)),0),o!==n&&t.successfulReplacements>0?(await c.default.writeFile(e.fullPath,o,"utf8"),t.success=!0,H++,w.info("File updated successfully",{path:e.path,successfulReplacements:t.successfulReplacements,failedReplacements:t.failedReplacements,linesReplaced:t.totalLinesReplaced,linesAdded:t.totalLinesAdded})):0===t.failedReplacements&&(t.success=!0),L+=t.failedReplacements,z+=t.totalLinesReplaced,B+=t.totalLinesAdded}catch(r){t.error=(0,f.getErrorMessage)(r),t.failedReplacements=e.replacements.length,L+=t.failedReplacements,w.error("File operation failed",{path:e.path,error:t.error})}N.push(t)}for(const e of
|
|
3567
|
+
t.replacements=s,t.successfulReplacements=s.filter((e=>e.success)).length,t.failedReplacements=s.filter((e=>!e.success)).length,t.totalLinesReplaced=s.filter((e=>e.success)).reduce(((e,t)=>e+(t.linesReplaced||0)),0),t.totalLinesAdded=s.filter((e=>e.success)).reduce(((e,t)=>e+(t.linesAdded||0)),0),o!==n&&t.successfulReplacements>0?(await c.default.writeFile(e.fullPath,o,"utf8"),t.success=!0,H++,w.info("File updated successfully",{path:e.path,successfulReplacements:t.successfulReplacements,failedReplacements:t.failedReplacements,linesReplaced:t.totalLinesReplaced,linesAdded:t.totalLinesAdded})):0===t.failedReplacements&&(t.success=!0),L+=t.failedReplacements,z+=t.totalLinesReplaced,B+=t.totalLinesAdded}catch(r){t.error=(0,f.getErrorMessage)(r),t.failedReplacements=e.replacements.length,L+=t.failedReplacements,w.error("File operation failed",{path:e.path,error:t.error})}N.push(t)}for(const e of P){const n={type:"document",documentId:e.documentId,success:!1,replacements:[],successfulReplacements:0,failedReplacements:0,totalLinesReplaced:0,totalLinesAdded:0}
|
|
3696
3568
|
try{const o=await t.documentFileManager.getDocumentAsFile(e.documentId),s=t.documentFileManager.getCachedDocumentInfo(e.documentId)
|
|
3697
3569
|
n.filename=s?.filename
|
|
3698
3570
|
const i=await c.default.readFile(o,"utf8"),{newContent:a,results:l}=await r(i,e.replacements)
|
|
3699
|
-
n.replacements=l,n.successfulReplacements=l.filter((e=>e.success)).length,n.failedReplacements=l.filter((e=>!e.success)).length,n.totalLinesReplaced=l.filter((e=>e.success)).reduce(((e,t)=>e+(t.linesReplaced||0)),0),n.totalLinesAdded=l.filter((e=>e.success)).reduce(((e,t)=>e+(t.linesAdded||0)),0),a!==i&&n.successfulReplacements>0?(await c.default.writeFile(o,a,"utf8"),t.documentFileManager.markForSync(e.documentId),n.success=!0,H++,w.info("Document updated successfully",{documentId:e.documentId,filename:n.filename,successfulReplacements:n.successfulReplacements,failedReplacements:n.failedReplacements,linesReplaced:n.totalLinesReplaced,linesAdded:n.totalLinesAdded})):0===n.failedReplacements&&(n.success=!0),L+=n.failedReplacements,z+=n.totalLinesReplaced,B+=n.totalLinesAdded}catch(t){n.error=(0,f.getErrorMessage)(t),n.failedReplacements=e.replacements.length,L+=n.failedReplacements,w.error("Document operation failed",{documentId:e.documentId,error:n.error})}N.push(n)}if(
|
|
3700
|
-
r?.success&&await t.documentFileManager.syncDocument(e.documentId)}}catch(e){w.warn("Some documents may not have synced properly",{error:e})}const U=await u.handleMultiFileGitCommit(_,
|
|
3701
|
-
try{await o.updateToolRecord(I,{metadata:{path:
|
|
3702
|
-
if(t.workspaceManager&&(Z+=`**Branch:** \`${t.workspaceManager.getCurrentContext().branchName}\`\n\n`),Z+="**Summary:**\n",Z+=`- **Files processed:** ${
|
|
3571
|
+
n.replacements=l,n.successfulReplacements=l.filter((e=>e.success)).length,n.failedReplacements=l.filter((e=>!e.success)).length,n.totalLinesReplaced=l.filter((e=>e.success)).reduce(((e,t)=>e+(t.linesReplaced||0)),0),n.totalLinesAdded=l.filter((e=>e.success)).reduce(((e,t)=>e+(t.linesAdded||0)),0),a!==i&&n.successfulReplacements>0?(await c.default.writeFile(o,a,"utf8"),t.documentFileManager.markForSync(e.documentId),n.success=!0,H++,w.info("Document updated successfully",{documentId:e.documentId,filename:n.filename,successfulReplacements:n.successfulReplacements,failedReplacements:n.failedReplacements,linesReplaced:n.totalLinesReplaced,linesAdded:n.totalLinesAdded})):0===n.failedReplacements&&(n.success=!0),L+=n.failedReplacements,z+=n.totalLinesReplaced,B+=n.totalLinesAdded}catch(t){n.error=(0,f.getErrorMessage)(t),n.failedReplacements=e.replacements.length,L+=n.failedReplacements,w.error("Document operation failed",{documentId:e.documentId,error:n.error})}N.push(n)}if(P.length>0)try{for(const e of P){const r=N.find((t=>t.documentId===e.documentId))
|
|
3572
|
+
r?.success&&await t.documentFileManager.syncDocument(e.documentId)}}catch(e){w.warn("Some documents may not have synced properly",{error:e})}const U=await u.handleMultiFileGitCommit(_,R,N,H,{operationType:"Replace lines",toolRecordId:I,successField:"successfulReplacements",logger:w,metrics:a,metricsPrefix:"replace_lines"},t),G=u.processMultiFileOperationResults(N,"successfulReplacements"),{successfulOperations:W,failedOperations:V,totalSuccessfulChanges:J,overallSuccess:K,successfulFiles:Y,failedFiles:Q}=G
|
|
3573
|
+
try{await o.updateToolRecord(I,{metadata:{path:R.length>0?R[0].path:"document:"+P[0]?.documentId,status:K?"completed":"failed",error:K?void 0:V+" operations failed",totalOperations:N.length,successfulFiles:Y,failedFiles:Q,operations:A,totalSuccessfulReplacements:J,totalFailedReplacements:L,totalLinesReplaced:z,totalLinesAdded:B,operationsWithChanges:H,processingTime:Date.now()-k,userComment:q,...R.length>0&&U.success&&U.commitHash&&{commitHash:U.commitHash,previousCommitHash:U.previousCommitHash||void 0}},note:K?`Line replacement completed: ${W}/${N.length} operations successful${R.length>0?" (committed to git)":""}`:`Line replacement partially failed: ${V}/${N.length} operations failed`})}catch(e){w.warn("Failed to update tool record",{recordError:e})}let Z="## Line Replacement Results\n\n"
|
|
3574
|
+
if(t.workspaceManager&&(Z+=`**Branch:** \`${t.workspaceManager.getCurrentContext().branchName}\`\n\n`),Z+="**Summary:**\n",Z+=`- **Files processed:** ${W+V}\n`,Z+=`- **Successful operations:** ${W}\n`,Z+=`- **Failed operations:** ${V}\n`,Z+=`- **Total replacements:** ${J} successful, ${L} failed\n`,Z+=`- **Total Lines Replaced:** ${z}\n`,B>0&&(Z+=`- **Total Lines Added:** ${B}\n`),Z+="\n",U.success&&U.commitHash&&(Z+="**Git Commit:**\n",Z+=`- **Commit Hash:** ${U.commitHash.substring(0,8)}\n`,Z+=`- **Files Committed:** ${U.filesCommitted.length}\n`,U.previousCommitHash&&(Z+=`- **Previous Commit:** ${U.previousCommitHash.substring(0,8)}\n`),Z+="\n"),D.lockAcquired&&D.lockedRequestId&&(Z+=`\u{1f512} **Locked request:** ${D.lockedRequestId}\n\n`),1===N.length){const e=N[0]
|
|
3703
3575
|
if(Z+=`**Operation:** ${e.success?"\u2705 Success":"\u274c Failed"}\n`,"file"===e.type?Z+=`**File:** ${e.path}\n`:(Z+="**Document:** "+e.documentId,e.filename&&(Z+=` (${e.filename})`),Z+="\n"),e.error?Z+=`**Error:** ${e.error}\n`:(Z+=`**Replacements:** ${e.successfulReplacements} successful`,e.failedReplacements>0&&(Z+=`, ${e.failedReplacements} failed`),Z+="\n",Z+=`**Lines Replaced:** ${e.totalLinesReplaced}\n`,e.totalLinesAdded>0&&(Z+=`**Lines Added:** ${e.totalLinesAdded}\n`)),e.replacements.some((e=>!e.success))){Z+="**Failed Replacement Details:**\n"
|
|
3704
|
-
for(const t of e.replacements.filter((e=>!e.success)))Z+=`- Replace ${"number"==typeof t.lines?"line "+t.lines:Array.isArray(t.lines)?`lines [${t.lines.join(", ")}]`:`lines ${t.lines.start}-${t.lines.end}`}: ${t.error}\n`}}else{Z+="**Summary:**\n",Z+=`- **Total Operations:** ${N.length}\n`,Z+=`- **Successful:** ${
|
|
3576
|
+
for(const t of e.replacements.filter((e=>!e.success)))Z+=`- Replace ${"number"==typeof t.lines?"line "+t.lines:Array.isArray(t.lines)?`lines [${t.lines.join(", ")}]`:`lines ${t.lines.start}-${t.lines.end}`}: ${t.error}\n`}}else{Z+="**Summary:**\n",Z+=`- **Total Operations:** ${N.length}\n`,Z+=`- **Successful:** ${W}\n`,Z+=`- **Failed:** ${V}\n`,Z+=`- **Total Replacements:** ${J} successful, ${L} failed\n`,Z+=`- **Total Lines Replaced:** ${z}\n`,B>0&&(Z+=`- **Total Lines Added:** ${B}\n`),Z+="\n",Z+="**Detailed Results:**\n\n"
|
|
3705
3577
|
for(const e of N){if("file"===e.type?Z+=`### File: ${e.path}\n`:(Z+="### Document: "+e.documentId,e.filename&&(Z+=` (${e.filename})`),Z+="\n"),Z+=`- **Status:** ${e.success?"\u2705 Success":"\u274c Failed"}\n`,e.error&&(Z+=`- **Error:** ${e.error}\n`),Z+=`- **Replacements:** ${e.successfulReplacements} successful`,e.failedReplacements>0&&(Z+=`, ${e.failedReplacements} failed`),Z+="\n",Z+=`- **Lines Replaced:** ${e.totalLinesReplaced}\n`,e.totalLinesAdded>0&&(Z+=`- **Lines Added:** ${e.totalLinesAdded}\n`),e.replacements.some((e=>!e.success))){Z+="- **Failed Replacement Details:**\n"
|
|
3706
|
-
for(const t of e.replacements.filter((e=>!e.success)))Z+=` - Replace ${"number"==typeof t.lines?"line "+t.lines:Array.isArray(t.lines)?`lines [${t.lines.join(", ")}]`:`lines ${t.lines.start}-${t.lines.end}`}: ${t.error}\n`}Z+="\n"}}
|
|
3578
|
+
for(const t of e.replacements.filter((e=>!e.success)))Z+=` - Replace ${"number"==typeof t.lines?"line "+t.lines:Array.isArray(t.lines)?`lines [${t.lines.join(", ")}]`:`lines ${t.lines.start}-${t.lines.end}`}: ${t.error}\n`}Z+="\n"}}P.length>0&&(Z+="\u{1f4c4} **Document Changes:** Modified documents have been automatically synced back to the tracking system.\n\n")
|
|
3707
3579
|
const X=Date.now()-k
|
|
3708
|
-
return w.info("Replace lines operation completed",{duration:X,success:K,totalOperations:N.length,successfulOperations:
|
|
3580
|
+
return w.info("Replace lines operation completed",{duration:X,success:K,totalOperations:N.length,successfulOperations:W,failedOperations:V}),a.incrementCounter("replace_lines_total",1,{success:K}),{content:[{type:"text",text:Z}],isError:!K}}catch(t){const r=Date.now()-k
|
|
3709
3581
|
if(w.error("Replace lines operation failed",{error:t instanceof Error?t.stack:t+"",duration:r,phase:v}),I)try{await o.updateToolRecord(I,{metadata:{path:e?.operations?.[0]?.path||e?.operations?.[0]?.documentId,status:"failed",error:(0,f.getErrorMessage)(t),phase:v,duration:r,userComment:e?.comment},note:"Line replacement failed: "+(0,f.getErrorMessage)(t)})}catch(e){}return a.incrementCounter("replace_lines_errors",1,{phase:v}),{content:[{type:"text",text:"\u274c **Replace Lines Failed:** "+(0,f.getErrorMessage)(t)}],isError:!0}}}
|
|
3710
3582
|
const c=a(t(1943)),l=t(6183),u=i(t(5967)),d=t(9860),h=t(5003),g=t(7478),p=t(9949),f=t(8824),m=t(3255),y=t(9470)},6688(e,exports,t){"use strict"
|
|
3711
3583
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.sessionIdentity=void 0
|
|
@@ -3767,11 +3639,11 @@ s.info("Getting file changes for task "+g,{showDiff:p})
|
|
|
3767
3639
|
const f=r.getTaskClient(),m=r.getToolRecordClient(),y=t.projectId
|
|
3768
3640
|
let w
|
|
3769
3641
|
r.setProjectId(y)
|
|
3770
|
-
try{const
|
|
3771
|
-
s.info("Raw task response data",{responseDataType:typeof
|
|
3772
|
-
try{const
|
|
3773
|
-
if(s.info("Raw records response data",{responseDataType:typeof
|
|
3774
|
-
k.forEach((e=>{x[e.type]=(x[e.type]||0)+1})),s.info("Record type distribution:",x)}}catch(
|
|
3642
|
+
try{const R=await f.getTask(g)
|
|
3643
|
+
s.info("Raw task response data",{responseDataType:typeof R,isArray:Array.isArray(R),hasData:null!=R,properties:R&&"object"==typeof R?Object.keys(R):[]}),w=(0,l.extractDataFromResponse)(R,{logger:s,operationName:"getTask",defaultValue:{id:g,title:"Unknown Task",status:"unknown",description:"No description available"}}),s.info("Found task: "+w.title)}catch(P){s.warn("Could not fetch task information: "+(0,d.getErrorMessage)(P)),w={id:g,title:"Unknown Task",status:"unknown",description:"No description available"}}let k=[]
|
|
3644
|
+
try{const M=await m.getToolRecordsByTaskId(g)
|
|
3645
|
+
if(s.info("Raw records response data",{responseDataType:typeof M,isArray:Array.isArray(M),hasData:null!=M,properties:M&&"object"==typeof M?Object.keys(M):[]}),k=(0,l.extractArrayFromResponse)(M,{logger:s,operationName:"searchRecords",defaultValue:[]}),k.length>0&&s.info("First record summary:",{id:k[0].id,type:k[0].type,hasMetadata:!!k[0].metadata,hasCommitHash:!!k[0].metadata?.commitHash}),s.info(`Extracted ${k.length} records for task ${g}`),k.length>0){const x={}
|
|
3646
|
+
k.forEach((e=>{x[e.type]=(x[e.type]||0)+1})),s.info("Record type distribution:",x)}}catch(j){s.warn("Error fetching records for task "+g,{error:(0,d.getErrorMessage)(j)}),k=[]}if(0===k.length)return h({success:!0,recordCount:0}),{content:[{type:"text",text:`No records found for task ${g}.`}]}
|
|
3775
3647
|
function b(e){const t=new Map,r=new Map,n=[]
|
|
3776
3648
|
for(const o of e)if("move-file"===o.type&&o.metadata){const e=o.metadata.source||o.metadata.oldPath,s=o.metadata.destination||o.metadata.newPath
|
|
3777
3649
|
if(e&&s){const i={source:e,destination:s,recordId:o.id,timestamp:o.createdAt,type:"move-file"}
|
|
@@ -3791,8 +3663,8 @@ let n=!1
|
|
|
3791
3663
|
if(t&&(n=e.metadata.successfulOperations.some((e=>e&&e.source&&e.destination))),!n&&r&&(n=e.metadata.failedOperations.some((e=>e&&e.source&&e.destination))),!n)return s.warn("Skipping move-files record without valid operation paths: "+e.id),!1}else if("delete-file"===e.type){if(!e.metadata.path)return s.warn("Skipping delete-file record without path metadata: "+e.id),!1}else if("delete-files"===e.type){const t=e.metadata.paths
|
|
3792
3664
|
if(!Array.isArray(t)||0===t.length)return s.warn("Skipping delete-files record without valid paths array: "+e.id),!1
|
|
3793
3665
|
if(!t.every((e=>"string"==typeof e&&e.trim().length>0)))return s.warn("Skipping delete-files record without valid file paths: "+e.id),!1}return!0}))
|
|
3794
|
-
if(s.info(`Found ${v.length} file operation records`),v.length>0){const
|
|
3795
|
-
v.forEach((e=>{
|
|
3666
|
+
if(s.info(`Found ${v.length} file operation records`),v.length>0){const O={}
|
|
3667
|
+
v.forEach((e=>{O[e.type]=(O[e.type]||0)+1})),s.info("Filtered record type distribution:",O)}if(0===v.length)return h({success:!0,fileChanges:0}),{content:[{type:"text",text:`No file changes found for task ${g}.`}]}
|
|
3796
3668
|
const C=new Map
|
|
3797
3669
|
v.forEach((e=>{let t=null
|
|
3798
3670
|
if(e.metadata){if(!e.metadata.commitHash){const t=["gitCommitId","commitId","commit","gitCommit"]
|
|
@@ -3838,43 +3710,43 @@ ee=await t.git.diff(oe),_.set(A,{firstChange:Q,lastChange:Z,hasDiff:!(!ee||0>=ee
|
|
|
3838
3710
|
continue}const z=L[0],B=L[L.length-1]
|
|
3839
3711
|
s.info(`First commit: ${z.commitHash?z.commitHash:"unknown"}, Last commit: ${B.commitHash?B.commitHash:"unknown"}`)
|
|
3840
3712
|
let H=null,U=!1
|
|
3841
|
-
if(t.git&&z.commitHash)try{H=await(0,c.findPreviousCommit)(t.git,A,z.commitHash),H?(U=!0,s.info(`Found previous commit: ${H} for ${A}`)):s.info(`No previous commit found for ${A}, likely a new file`)}catch(ae){s.warn("Error finding previous commit for "+A,{error:(0,d.getErrorMessage)(ae)})}const
|
|
3842
|
-
if(s.info(`Using ${U?"pre-task":"first task"} commit as baseline for ${A}: ${
|
|
3713
|
+
if(t.git&&z.commitHash)try{H=await(0,c.findPreviousCommit)(t.git,A,z.commitHash),H?(U=!0,s.info(`Found previous commit: ${H} for ${A}`)):s.info(`No previous commit found for ${A}, likely a new file`)}catch(ae){s.warn("Error finding previous commit for "+A,{error:(0,d.getErrorMessage)(ae)})}const G=U&&H?{...z,commitHash:H,status:"pre-task"}:z
|
|
3714
|
+
if(s.info(`Using ${U?"pre-task":"first task"} commit as baseline for ${A}: ${G.commitHash}`),s.info(`Last commit for ${A}: ${B.commitHash}`),s.info("Commits are "+(G.commitHash===B.commitHash?"identical":"different")),z.commitHash===B.commitHash&&!U){if(p&&!U&&t.git&&B.commitHash)try{const ce=[`${B.commitHash}:${A}`]
|
|
3843
3715
|
s.info(`Getting new file content using git show: ${B.commitHash?B.commitHash.substring(0,8):"unknown"}:${A}`)
|
|
3844
3716
|
const le=await t.git.show(ce)
|
|
3845
3717
|
if(le&&le.trim().length>0){let ue=""
|
|
3846
3718
|
const de=le.split("\n")
|
|
3847
3719
|
for(const he of de)ue+=`+${he}\n`
|
|
3848
|
-
_.set(A,{firstChange:
|
|
3849
|
-
continue}}catch(ge){s.warn("Error getting new file content for "+A,{error:(0,d.getErrorMessage)(ge)})}_.set(A,{firstChange:
|
|
3850
|
-
continue}if(z.commitHash===B.commitHash&&U){if(H===z.commitHash){_.set(A,{firstChange:
|
|
3851
|
-
continue}s.info("Special case: First and last task commits are the same, but pre-task commit is different")}let
|
|
3852
|
-
if(p||"pre-task"!==
|
|
3720
|
+
_.set(A,{firstChange:G,lastChange:B,hasDiff:!0,diffText:ue}),s.info(`Formatted new file content as diff, ${de.length} lines`)
|
|
3721
|
+
continue}}catch(ge){s.warn("Error getting new file content for "+A,{error:(0,d.getErrorMessage)(ge)})}_.set(A,{firstChange:G,lastChange:B,hasDiff:!1,diffText:"Only one commit available for this file"})
|
|
3722
|
+
continue}if(z.commitHash===B.commitHash&&U){if(H===z.commitHash){_.set(A,{firstChange:G,lastChange:B,hasDiff:!1,diffText:"No changes detected"})
|
|
3723
|
+
continue}s.info("Special case: First and last task commits are the same, but pre-task commit is different")}let W="",V=!1
|
|
3724
|
+
if(p||"pre-task"!==G.status){try{if(t.git){try{await t.git.show([`${B.commitHash}:${A}`])}catch(fe){s.warn(`File ${A} does not exist in commit ${B.commitHash}, might be deleted or moved`),W="File was deleted or moved from this location during the task",V=!0,_.set(A,{firstChange:G,lastChange:B,hasDiff:V,diffText:W})
|
|
3853
3725
|
continue}let pe
|
|
3854
|
-
if("pre-task"===
|
|
3855
|
-
try{const me=await t.git.show([`${
|
|
3856
|
-
if(me!==ye&&(V=!0,
|
|
3857
|
-
Math.abs(we.length-ke.length)>0&&(
|
|
3726
|
+
if("pre-task"===G.status?(pe=[`${G.commitHash}..${B.commitHash}`,"--",A],s.info(`Comparing pre-task commit with final commit: ${G.commitHash?G.commitHash.substring(0,8):"unknown"}..${B.commitHash?B.commitHash.substring(0,8):"unknown"} for ${A}`)):(pe=["4b825dc642cb6eb9a060e54bf8d69288fbee4904.."+B.commitHash,"--",A],s.info(`File created during task, showing full file diff using empty tree object: ${B.commitHash?B.commitHash.substring(0,8):"unknown"} for ${A}`)),W=await t.git.diff(pe),V=!!W&&W.trim().length>0,!V&&G.commitHash!==B.commitHash){s.info("No diff found between commits but commits are different, trying direct file content comparison")
|
|
3727
|
+
try{const me=await t.git.show([`${G.commitHash}:${A}`]),ye=await t.git.show([`${B.commitHash}:${A}`])
|
|
3728
|
+
if(me!==ye&&(V=!0,W="Changes detected through direct content comparison (not visible in standard diff)",p)){const we=me.split("\n"),ke=ye.split("\n")
|
|
3729
|
+
Math.abs(we.length-ke.length)>0&&(W+=`\n\nLine count changed: ${we.length} \u2192 ${ke.length}`),me.includes("\0")||ye.includes("\0")?W+="\n\nBinary content detected - changes not displayed":me.replace(/\s+/g,"")===ye.replace(/\s+/g,"")&&(W+="\n\nWhitespace-only changes detected")}}catch(be){s.warn("Error in direct file comparison: "+(be instanceof Error?be.message:be+""))}}s.info(`Diff generation result for ${A}: hasDiff=${V}, length=${W.length}`)}}catch(Ie){if(s.warn("Error getting diff for "+A,{error:(0,d.getErrorMessage)(Ie),firstCommit:z.commitHash||"unknown",lastCommit:B.commitHash||"unknown"}),W="Error getting diff: "+(0,d.getErrorMessage)(Ie),"pre-task"!==z.status&&t.git)try{const ve=[`${B.commitHash}:${A}`]
|
|
3858
3730
|
s.info(`Trying fallback to show file content using git show: ${B.commitHash?B.commitHash.substring(0,8):"unknown"}:${A}`)
|
|
3859
3731
|
const Ce=await t.git.show(ve)
|
|
3860
3732
|
if(Ce&&Ce.trim().length>0){if(p){let _e=""
|
|
3861
3733
|
const Ee=Ce.split("\n")
|
|
3862
3734
|
for(const qe of Ee)_e+=`+${qe}\n`
|
|
3863
|
-
|
|
3864
|
-
V=!0,s.info("Fallback succeeded, got file content of length "+Ce.length)}}catch(Se){s.warn("Fallback also failed for "+A,{error:Se instanceof Error?Se.message:Se+""})}}_.set(A,{firstChange:
|
|
3735
|
+
W=_e}else W="File created during this task. Content:\n"+Ce
|
|
3736
|
+
V=!0,s.info("Fallback succeeded, got file content of length "+Ce.length)}}catch(Se){s.warn("Fallback also failed for "+A,{error:Se instanceof Error?Se.message:Se+""})}}_.set(A,{firstChange:G,lastChange:B,hasDiff:V,diffText:W||"No changes detected between commits"})}else V=G.commitHash!==B.commitHash,W=V?"File has changes":"No changes detected between commits",_.set(A,{firstChange:G,lastChange:B,hasDiff:V,diffText:W})}let E=`# File Changes for Task: ${g}\n\n`
|
|
3865
3737
|
w&&"object"==typeof w&&(E+="## Task Information\n",E+=`- **Title**: ${w.title||"Unknown"}\n`,E+=`- **Status**: ${w.status||"Unknown"}\n`,E+=`- **Description**: ${w.description||"No description"}\n\n`)
|
|
3866
3738
|
const q=3e3
|
|
3867
3739
|
let S=0,T=!1
|
|
3868
3740
|
if(p){for(const Te of _.values())Te.hasDiff&&Te.diffText&&(S+=Te.diffText.split("\n").length)
|
|
3869
3741
|
T=S>q,s.info(`Total diff size: ${S} lines (limit: ${q} lines)`),s.info(`Diffs ${T?"will be limited":"will be shown"} based on size`)}if(E+="## Summary\n",E+=`- **Files Modified**: ${C.size}\n`,E+=`- **Total File Operations**: ${v.length}\n`,E+="- **What's Shown**: For existing files, comparing state before task started with final state.\n",E+=" For files created during task, showing the entire file as created.\n",T?(E+=`- **Diff Display**: Limited (total diff size of ${S} lines exceeds limit of ${q} lines)\n`,E+=" Use file-history tool with individual files to see detailed changes\n\n"):E+=`- **Diff Display**: ${p?"Enabled":"Disabled"} (use showDiff=${!p} to ${p?"hide":"show"} diffs)\n\n`,I.allMoves.length>0){E+="## Move Operations\n\n",E+=`Detected ${I.allMoves.length} file move operation(s):\n\n`
|
|
3870
|
-
for(const
|
|
3871
|
-
for(const[
|
|
3872
|
-
let
|
|
3873
|
-
try{await a.access(
|
|
3874
|
-
const $e=new Date(
|
|
3875
|
-
E+=`**First Change**: ${$e}\n`,E+=`**Last Change**: ${De}\n`,"pre-task"===
|
|
3876
|
-
const Ae=I.sourceToMove.get(
|
|
3877
|
-
Ae?E+=`**\u2139\ufe0f Move Operation**: This file was moved TO **${Ae.destination}**\n`:Fe&&(E+=`**\u2139\ufe0f Move Operation**: This file was moved FROM **${Fe.source}**\n`),p&&!T?
|
|
3742
|
+
for(const Re of I.allMoves)E+=`- **${Re.source}** \u2192 **${Re.destination}**\n`,E+=` - Operation: ${Re.type}\n`,E+=` - Timestamp: ${new Date(Re.timestamp).toLocaleString()}\n`,E+=` - Record ID: ${Re.recordId}\n\n`}E+="## Modified Files\n\n"
|
|
3743
|
+
for(const[Pe,Me]of _.entries()){const{normalizedPath:xe,fullPath:je}=u.validateAndNormalizePath(Pe,t)
|
|
3744
|
+
let Oe=!1
|
|
3745
|
+
try{await a.access(je),Oe=!0}catch{}E+=`### ${Pe} ${Oe?"":"(Deleted)"}\n\n`
|
|
3746
|
+
const $e=new Date(Me.firstChange.timestamp).toLocaleString(),De=new Date(Me.lastChange.timestamp).toLocaleString()
|
|
3747
|
+
E+=`**First Change**: ${$e}\n`,E+=`**Last Change**: ${De}\n`,"pre-task"===Me.firstChange.status&&Me.firstChange.commitHash?E+=`**Pre-Task Commit**: ${Me.firstChange.commitHash.substring(0,8)}\n`:Me.firstChange.commitHash&&(E+=`**File Created During Task**: ${Me.firstChange.commitHash.substring(0,8)}\n`),Me.lastChange.commitHash&&(E+=`**Final Commit**: ${Me.lastChange.commitHash.substring(0,8)}\n`)
|
|
3748
|
+
const Ae=I.sourceToMove.get(Pe),Fe=I.destToMove.get(Pe)
|
|
3749
|
+
Ae?E+=`**\u2139\ufe0f Move Operation**: This file was moved TO **${Ae.destination}**\n`:Fe&&(E+=`**\u2139\ufe0f Move Operation**: This file was moved FROM **${Fe.source}**\n`),p&&!T?Me.hasDiff?(E+="\n**Changes**:\n",E+="```diff\n",E+=Me.diffText,E+="\n```\n\n"):E+=`\n**Note**: ${Me.diffText}\n\n`:T&&Me.hasDiff?(E+=`\n**Note**: File has changes (${Me.diffText?Me.diffText.split("\n").length:0} lines). `,E+=`Compare ${Me.firstChange.commitHash?Me.firstChange.commitHash.substring(0,8):"unknown"}..${Me.lastChange.commitHash?Me.lastChange.commitHash.substring(0,8):"unknown"} to see changes.\n\n`):Me.hasDiff?E+="\n**Note**: File has changes. Use showDiff=true to see the diff.\n\n":E+=`\n**Note**: ${Me.diffText}\n\n`,E+="---\n\n"}return h({success:!0,fileCount:C.size}),{content:[{type:"text",text:E}]}}catch(Ne){return s.error("Error in task file history tool",{error:Ne instanceof Error?Ne.stack:Ne+""}),h({success:!1,error:Ne instanceof Error?Ne.name:"unknown"}),{content:[{type:"text",text:"Error: "+(0,d.getErrorMessage)(Ne)}],isError:!0}}}
|
|
3878
3750
|
const i=t(9860),a=s(t(1943)),c=t(9671),l=t(2960),u=s(t(5967)),d=t(8824)},6928(module){"use strict"
|
|
3879
3751
|
module.exports=require("path")},6975(e,exports,t){"use strict"
|
|
3880
3752
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.ProjectClientAdapter=void 0
|
|
@@ -4023,20 +3895,24 @@ if(e){const t=c.getCLISessionClient()
|
|
|
4023
3895
|
if(t){const r=await t.getByExternalId(e)
|
|
4024
3896
|
if(r?.workflowId){const e=await c.proxyGet("/api/workflows/"+r.workflowId),t=e?.data||e
|
|
4025
3897
|
t?.approvalMode&&(y=(0,a.getApprovalMode)(t.approvalMode))}}}if("none"===y)try{const e=await c.proxyGet("/api/projects/"+f),t=e?.data||e,r=t?.metadata?.defaultApprovalMode
|
|
4026
|
-
r&&(y=(0,a.getApprovalMode)(r))}catch(e){g.warn("Failed to read project metadata for approvalMode fallback",{error:(0,i.getErrorMessage)(e)})}}catch(e){g.warn("Failed to resolve approval mode, using default",{error:(0,i.getErrorMessage)(e)})}const w="require-approval"===y&&"quick-edit"!==l.type?"pending_approval":"open"
|
|
3898
|
+
r&&(y=(0,a.getApprovalMode)(r))}catch(e){g.warn("Failed to read project metadata for approvalMode fallback",{error:(0,i.getErrorMessage)(e)})}}catch(e){g.warn("Failed to resolve approval mode, using default",{error:(0,i.getErrorMessage)(e)})}const w="require-approval"===y&&"quick-edit"!==l.type?"pending_approval":"open"
|
|
3899
|
+
let k=h
|
|
3900
|
+
if(h?.sessionId)try{const e=c.getCLISessionClient()
|
|
3901
|
+
if(e){const t=await e.getByExternalId(h.sessionId)
|
|
3902
|
+
"planner"!==t?.agentType&&"auto-planner"!==t?.agentType||(k=void 0,g.info("Skipping cliOrigin for planner-created request",{agentType:t.agentType}))}}catch{}const b={title:l.title,description:l.description,type:l.type,acceptanceCriteria:l.acceptanceCriteria,status:w,...l.planDocumentId&&{planDocumentId:l.planDocumentId},...k&&{cliOrigin:k}}
|
|
4027
3903
|
g.info("Creating request via request client",{projectId:f,title:l.title,type:l.type,criteriaCount:l.acceptanceCriteria.length})
|
|
4028
|
-
const
|
|
4029
|
-
g.debug("Create request response structure",{type:typeof
|
|
4030
|
-
const
|
|
4031
|
-
let
|
|
4032
|
-
if(d?.workspaceManager)try{await d.workspaceManager.initializeRequest(
|
|
4033
|
-
g.info("Request created successfully",{requestId:
|
|
3904
|
+
const I=await m.createRequest(b)
|
|
3905
|
+
g.debug("Create request response structure",{type:typeof I,isArray:Array.isArray(I),hasData:null!=I,properties:I?Object.keys(I):[],dataPreview:I?JSON.stringify(I).substring(0,200)+"...":"null"})
|
|
3906
|
+
const v=(0,o.extractDataFromResponse)(I,{logger:g,operationName:"createRequest",throwOnNoData:!0}),C="data"in v?v.data:v
|
|
3907
|
+
let _,E={created:!1}
|
|
3908
|
+
if(d?.workspaceManager)try{await d.workspaceManager.initializeRequest(C.id,C.title),E={created:!0,branchName:"requests/"+C.id,message:"Branch created successfully"},g.info("Request branch initialized successfully",{requestId:C.id,branchName:E.branchName,title:C.title})}catch(e){g.warn("Failed to initialize request branch, will retry on first operation",{requestId:C.id,error:(0,i.getErrorMessage)(e)})}else"quick-edit"===l.type?g.info("Quick-edit request - skipping branch creation, will work directly on main",{requestId:C.id}):g.debug("No workspace manager available, branch creation deferred",{requestId:C.id})
|
|
3909
|
+
g.info("Request created successfully",{requestId:C.id,title:C.title,branchCreated:E.created,branchName:E.branchName})
|
|
4034
3910
|
try{const e=c.getToolRecordClient()
|
|
4035
|
-
if(e){const t=await e.createToolRecord({requestId:
|
|
4036
|
-
|
|
4037
|
-
const
|
|
4038
|
-
let
|
|
4039
|
-
return
|
|
3911
|
+
if(e){const t=await e.createToolRecord({requestId:C.id,projectId:f,type:"create-request",metadata:{status:"completed",timestamp:(new Date).toISOString(),requestType:C.type,requestTitle:C.title,requestDescription:C.description,criteriaCount:C.acceptanceCriteria.length,branchCreated:E.created,branchName:E.created?E.branchName:null},note:`Created request "${C.title}" of type ${C.type}${E.created?" with branch "+E.branchName:" - branch will be created on first file operation"}`})
|
|
3912
|
+
_=t?.id}}catch(e){g.warn("Failed to create tool record for request creation",{error:(0,i.getErrorMessage)(e),requestId:C.id})}p({success:!0,type:l.type,hasProjectId:!0}),g.info("Request created successfully",{requestId:C.id,title:C.title,type:C.type,projectId:f})
|
|
3913
|
+
const q=C.localId||C.id
|
|
3914
|
+
let S="pending_approval"===w?`Created Request ${q} (pending approval)`:"Created Request "+q
|
|
3915
|
+
return _&&(S+=`\n[RECORD:${_}]`),{content:[{type:"text",text:S}]}}catch(r){if(g.error("Failed to create request",{error:r instanceof Error?r.stack:r+"",args:e}),t.projectId)try{if(r instanceof Error&&(r.message.includes("Project is disabled")||r.message.includes("Project cannot accept new requests")||r.message.includes("disabled due to tier limits")))g.info("Skipping tool record creation for disabled project error",{projectId:t.projectId,error:r.message})
|
|
4040
3916
|
else{const n=c.getToolRecordClient()
|
|
4041
3917
|
n&&await n.createToolRecord({projectId:t.projectId,type:"create-request",metadata:{status:"failed",timestamp:(new Date).toISOString(),requestTitle:e.title,requestType:e.type,requestDescription:e.description?.substring(0,100)+(e.description?.length>100?"...":""),criteriaCount:e.acceptanceCriteria?e.acceptanceCriteria.length:0,branchCreated:!1,branchName:null,error:(0,i.getErrorMessage)(r),errorDetails:r instanceof Error?r.stack:r+""},note:"Failed to create request: "+e.title})}}catch(e){g.error("Failed to create failure record for request creation",{error:e instanceof Error?e.message:e+""})}if(p({success:!1,error:r instanceof Error?r.name:"unknown"}),r instanceof s.ZodError&&r.errors.length>0){const e=r.errors[0]
|
|
4042
3918
|
let t=e.message
|
|
@@ -4246,37 +4122,32 @@ return t.warn("Failed to get current git branch",{error:o}),r.incrementCounter("
|
|
|
4246
4122
|
try{if(!t.git)return r.debug("No git repository available"),n.incrementCounter("find_feature_branch_no_git",1),o({success:!1,reason:"no_git"}),{found:!1}
|
|
4247
4123
|
const s=await d.getRepositoryStatus(t.git,r,n),i=s.branches.filter((t=>t.name==="requests/"+e)),a=i.length>0,c=a?i[0].name:void 0,l=i.map((e=>e.name))
|
|
4248
4124
|
return r.debug("Searched for feature branch",{requestId:e,found:a,branchName:c,matchingBranches:l.length,totalBranches:s.branches.length}),n.incrementCounter("find_feature_branch_success",1,{found:a.toString()}),o({success:!0,found:a.toString()}),{found:a,branchName:c,allBranches:l}}catch(t){const s=(0,g.getErrorMessage)(t)
|
|
4249
|
-
return r.warn("Failed to find feature branch for request",{requestId:e,error:s}),n.incrementCounter("find_feature_branch_failure",1),o({success:!1,error:t instanceof Error?t.name:"unknown"}),{found:!1}}}async function o(e,o,s,i
|
|
4250
|
-
let
|
|
4251
|
-
try{
|
|
4252
|
-
const e=
|
|
4253
|
-
if(Date.now(),e.requestId===
|
|
4254
|
-
if(
|
|
4255
|
-
try{if("multi-agent"===
|
|
4256
|
-
|
|
4257
|
-
const
|
|
4258
|
-
if(Date.now(),
|
|
4259
|
-
let e=`Request ${
|
|
4260
|
-
if(
|
|
4261
|
-
t.lockOverride.enabled&&(e+=`\n\n**To take over this request (only if safe to do so), use switch_to_branch with password: \`${
|
|
4262
|
-
const
|
|
4263
|
-
if(Date.now(),!
|
|
4264
|
-
throw
|
|
4265
|
-
|
|
4266
|
-
const e=
|
|
4267
|
-
if(e.basePath&&(
|
|
4268
|
-
throw
|
|
4269
|
-
try{const{findLargeUntrackedFiles:
|
|
4270
|
-
if(a.length>0){const e=
|
|
4271
|
-
|
|
4272
|
-
return
|
|
4273
|
-
|
|
4274
|
-
if(!m.found||!m.branchName)return i.warn("No feature branch found for request during auto-switch",{requestId:o,availableBranches:m.allBranches||[]}),a.incrementCounter(c+"_auto_branch_switch_no_branch",1),{switched:!1,message:"No feature branch found for request "+o}
|
|
4275
|
-
const y=await r(s,i,a),w=await d.switchToBranch(s.git,m.branchName,i,a)
|
|
4276
|
-
return w.success?(s.updateBranchState&&await s.updateBranchState(m.branchName,o),i.info("Auto-switched to request branch after task promotion",{requestId:o,fromBranch:y,toBranch:m.branchName}),a.incrementCounter(c+"_auto_branch_switch_success",1),{switched:!0,branchName:m.branchName,message:"Switched to "+m.branchName}):(i.warn("Failed to auto-switch to request branch",{requestId:o,targetBranch:m.branchName,error:w.message}),a.incrementCounter(c+"_auto_branch_switch_failure",1),{switched:!1,message:"Failed to switch: "+w.message})}catch(e){if(e instanceof p.RequestLockError)throw i.warn("Auto-switch blocked by request lock in legacy mode, re-throwing lock error",{requestId:e.requestId,lockedByAgent:e.lockedByAgent,lockedAt:e.lockedAt}),e
|
|
4277
|
-
return i.error("Error during auto-switch to request branch",{requestId:o,error:(0,g.getErrorMessage)(e)}),a.incrementCounter(c+"_auto_branch_switch_error",1),{switched:!1,message:"Error during switch: "+(0,g.getErrorMessage)(e)}}}function s(e,t,r,n){if(!e.workspaceManager)return n.debug("No workspace manager available, skipping context validation",{operation:r,requestId:t}),{isValid:!0}
|
|
4125
|
+
return r.warn("Failed to find feature branch for request",{requestId:e,error:s}),n.incrementCounter("find_feature_branch_failure",1),o({success:!1,error:t instanceof Error?t.name:"unknown"}),{found:!1}}}async function o(e,r,n,o,s,i){if(!r||!n.git)return{switched:!1,message:"No branch switch needed"}
|
|
4126
|
+
let a=!1,c=Date.now()
|
|
4127
|
+
try{n.syncBranchState&&await n.syncBranchState(),Date.now(),c=Date.now()
|
|
4128
|
+
const e=n.getCurrentBranchContext?await n.getCurrentBranchContext():{branch:null,requestId:null,isMain:!0}
|
|
4129
|
+
if(Date.now(),e.requestId===r)return o.debug("Already in correct request context",{requestId:r,currentBranch:e.branch}),{switched:!1,branchName:e.branch||void 0,message:`Already in request ${r} context`,lockAcquired:!1}
|
|
4130
|
+
if(n.workspaceManager){o.debug("Using WorkspaceManager for request context switching",{requestId:r,currentMode:n.workspaceManager.getCurrentContext().mode})
|
|
4131
|
+
try{if("multi-agent"===n.workspaceManager.getCurrentContext().mode)if(o.debug("Multi-agent mode: checking request lock before auto-switch",{requestId:r}),n.apiClient)try{const e=n.apiClient.getRequestClient(),{sessionTag:t}=(0,h.getGlobalClientInfo)()
|
|
4132
|
+
c=Date.now()
|
|
4133
|
+
const s=await e.getRequestLockStatus(r)
|
|
4134
|
+
if(Date.now(),s.isLocked&&s.lockedBySessionTag!==t){o.warn("Auto-switch blocked by request lock",{requestId:r,lockedByAgent:s.lockedBySessionTag,currentAgent:t,lockedAt:s.lockedAt})
|
|
4135
|
+
let e=`Request ${r} is currently locked by another agent (${s.lockedBySessionTag}).\n\nLocked since: ${s.lockedAt||"unknown"}\n\nIn multi-agent mode, only one agent can work on a request at a time. Please wait for the other agent to complete their work or contact an administrator if the lock appears stale.`
|
|
4136
|
+
if(n.lockOverrideManager&&n.configManager)try{const t=await n.configManager.getEffectiveConfig(n.mainBasePath)
|
|
4137
|
+
t.lockOverride.enabled&&(e+=`\n\n**To take over this request (only if safe to do so), use switch_to_branch with password: \`${n.lockOverrideManager.generatePassword(r,t.lockOverride.passwordValidityMinutes)}\` (valid for ${t.lockOverride.passwordValidityMinutes} minutes)**`)}catch(e){o.warn("Failed to check lock override config",{error:e})}throw new p.RequestLockError(e,r,s.lockedBySessionTag,s.lockedAt)}if(!s.isLocked){c=Date.now(),o.debug("Acquiring lock for auto-switch",{requestId:r,sessionTag:t})
|
|
4138
|
+
const n=await e.lockRequest(r,t)
|
|
4139
|
+
if(Date.now(),!n.locked){const e=`Failed to acquire lock for request ${r} during auto-switch`
|
|
4140
|
+
throw o.warn("Auto-switch lock acquisition failed",{requestId:r}),Error(e)}o.info("Successfully acquired lock for auto-switch",{requestId:r,sessionTag:t,lockedAt:n.lockedAt}),a=!0}}catch(e){throw o.error("Lock check/acquisition failed during auto-switch",{requestId:r,error:e instanceof Error?e.message:e+""}),e}else o.warn("Multi-agent mode but no API client available for locking",{requestId:r})
|
|
4141
|
+
o.debug("Ensuring workspace is ready for file operations",{requestId:r,reason:"first-file-operation"}),c=Date.now(),await n.workspaceManager.ensureWorkspaceReady(r),Date.now()
|
|
4142
|
+
const e=n.workspaceManager.getCurrentContext()
|
|
4143
|
+
if(e.basePath&&(n.git=(0,u.simpleGit)(e.basePath),o.info("Updated git instance to worktree path",{requestId:r,gitWorkingDirectory:e.basePath,mode:e.mode,branchName:e.branchName})),e.requestId!==r){const t=`Workspace switch validation failed. Expected requestId: ${r}, but got: ${e.requestId}`
|
|
4144
|
+
throw o.error("Post-switch context validation failed",{requestId:r,expectedRequestId:r,actualRequestId:e.requestId,actualBasePath:e.basePath,mode:e.mode}),Error(t)}o.info("Workspace is ready via WorkspaceManager",{requestId:r,mode:n.workspaceManager.getCurrentContext().mode,workflow:"hybrid-creation-lazy-worktree",validation:"context_validated"})
|
|
4145
|
+
try{const{findLargeUntrackedFiles:s,formatLargeFileWarning:i}=await Promise.resolve().then(t.t.bind(t,7478,23)),a=await s(e.basePath)
|
|
4146
|
+
if(a.length>0){const e=i(a)
|
|
4147
|
+
n.workspaceManager.largeFileWarning=e,o.warn("Large untracked files detected",{requestId:r,fileCount:a.length,files:a.map((e=>({path:e.path,sizeMB:e.sizeMB})))})}}catch(e){o.debug("Large file check failed",{error:e})}return s.incrementCounter(i+"_auto_context_switch_success",1),{switched:!0,branchName:n.workspaceManager.getCurrentContext().branchName,message:"Workspace ready for request "+r,lockAcquired:a,lockedRequestId:a?r:void 0}}catch(e){if(e instanceof p.RequestLockError)throw o.warn("Auto-switch blocked by request lock, re-throwing lock error",{requestId:e.requestId,lockedByAgent:e.lockedByAgent,lockedAt:e.lockedAt}),e
|
|
4148
|
+
return o.error("Error switching to request context",{requestId:r,error:(0,g.getErrorMessage)(e)}),s.incrementCounter(i+"_auto_context_switch_error",1),{switched:!1,message:"Context switch error: "+(0,g.getErrorMessage)(e)}}}return o.error("WorkspaceManager not available - this should not happen",{requestId:r}),{switched:!1,message:"WorkspaceManager not available"}}catch(e){if(e instanceof p.RequestLockError)throw o.warn("Auto-switch blocked by request lock, re-throwing lock error",{requestId:e.requestId,lockedByAgent:e.lockedByAgent,lockedAt:e.lockedAt}),e
|
|
4149
|
+
return o.error("Error during auto-switch to request branch",{requestId:r,error:(0,g.getErrorMessage)(e)}),s.incrementCounter(i+"_auto_branch_switch_error",1),{switched:!1,message:"Error during switch: "+(0,g.getErrorMessage)(e)}}}function s(e,t,r,n){if(!e.workspaceManager)return n.debug("No workspace manager available, skipping context validation",{operation:r,requestId:t}),{isValid:!0}
|
|
4278
4150
|
const o=e.workspaceManager.getCurrentContext()
|
|
4279
|
-
if("multi-agent"!==o.mode)return n.debug("Single-agent mode detected, skipping multi-agent context validation",{operation:r,requestId:t,mode:o.mode}),{isValid:!0}
|
|
4280
4151
|
if(!t)return n.debug("File operation without requestId in multi-agent mode",{operation:r,currentContext:o.requestId,mode:o.mode,basePath:o.basePath}),{isValid:!0}
|
|
4281
4152
|
if(o.requestId!==t){const e=`Workspace context mismatch for ${r}. Expected requestId: ${t}, but current context is: ${o.requestId}. This suggests workspace switching failed or didn't occur. Current basePath: ${o.basePath}, branch: ${o.branchName}`
|
|
4282
4153
|
return n.error("Workspace context validation failed - context mismatch",{operation:r,expectedRequestId:t,currentRequestId:o.requestId,currentBasePath:o.basePath,currentBranchName:o.branchName,currentIsMainBranch:o.isMainBranch,mode:o.mode,issue:"request_id_mismatch"}),{isValid:!1,errorMessage:e}}if(o.isMainBranch&&t){const e=`File operation ${r} attempted with requestId ${t} but workspace is still in main branch (${o.branchName}). This indicates workspace switching to request context failed.`
|
|
@@ -4318,8 +4189,7 @@ try{const l=(await d.getRepositoryStatus(n.git,o,s)).branches.filter((t=>t.name=
|
|
|
4318
4189
|
if(0>=l.length)return o.debug("No feature branch found for request, staying on current branch",{requestId:e,currentBranch:a,taskId:t,filePath:r}),s.incrementCounter(i+"_branch_switch_no_feature_branch",1),{switched:!1,message:"No feature branch found for request "+e}
|
|
4319
4190
|
c=l[0].name,o.debug("Found matching request branch",{requestId:e,targetBranch:c,currentBranch:a})}catch(t){return o.warn("Could not check for request branches, continuing on current branch",{requestId:e,currentBranch:a,error:(0,g.getErrorMessage)(t)}),s.incrementCounter(i+"_branch_switch_branch_check_error",1),{switched:!1}}if(a===c)return o.debug("Already on correct branch for request",{requestId:e,branchName:a,taskId:t,filePath:r}),s.incrementCounter(i+"_branch_switch_already_correct",1),{switched:!1,branchName:a,message:"Already on correct branch "+a}
|
|
4320
4191
|
try{const l=await d.switchToBranch(n.git,c,o,s)
|
|
4321
|
-
return l.success?(o.info("Switched to feature branch for file operation",{requestId:e,taskId:t,filePath:r,fromBranch:a,toBranch:c}),s.incrementCounter(i+"_branch_switch_success",1),{switched:!0,branchName:c||void 0,message:`Switched to feature branch ${c} for this operation`}):(o.warn("Failed to switch to feature branch",{requestId:e,taskId:t,filePath:r,targetBranch:c,reason:l.message}),s.incrementCounter(i+"_branch_switch_failed",1),{switched:!1,message:"Failed to switch to branch: "+l.message})}catch(n){return o.warn("Error during branch switching",{requestId:e,taskId:t,filePath:r,targetBranch:c,error:(0,g.getErrorMessage)(n)}),s.incrementCounter(i+"_branch_switch_error",1),{switched:!1,message:"Error switching branches: "+(0,g.getErrorMessage)(n)}}}catch(n){return o.warn("Overall error in ensureCorrectBranch",{requestId:e,taskId:t,filePath:r,error:(0,g.getErrorMessage)(n)}),s.incrementCounter(i+"_branch_switch_overall_error",1),{switched:!1,message:"Branch switching error: "+(0,g.getErrorMessage)(n)}}},exports.autoSwitchToRequestBranch=o,exports.determineExpectedBranch=function(e,t,r){try{
|
|
4322
|
-
return r.debug("Single-agent mode: determined expected branch",{taskId:e,requestId:t.currentRequestId,expectedBranch:n}),n}return null}catch(t){return r.warn("Failed to determine expected branch for task",{taskId:e,error:(0,g.getErrorMessage)(t)}),null}},exports.validateWorkspaceContextForFileOperation=s,exports.ensureCorrectWorkspaceContext=async function(e){const{taskPromoted:t,requestId:r,context:n,operation:i,logger:a,metrics:c,metricsPrefix:l,requireRequestContext:u=!0}=e
|
|
4192
|
+
return l.success?(o.info("Switched to feature branch for file operation",{requestId:e,taskId:t,filePath:r,fromBranch:a,toBranch:c}),s.incrementCounter(i+"_branch_switch_success",1),{switched:!0,branchName:c||void 0,message:`Switched to feature branch ${c} for this operation`}):(o.warn("Failed to switch to feature branch",{requestId:e,taskId:t,filePath:r,targetBranch:c,reason:l.message}),s.incrementCounter(i+"_branch_switch_failed",1),{switched:!1,message:"Failed to switch to branch: "+l.message})}catch(n){return o.warn("Error during branch switching",{requestId:e,taskId:t,filePath:r,targetBranch:c,error:(0,g.getErrorMessage)(n)}),s.incrementCounter(i+"_branch_switch_error",1),{switched:!1,message:"Error switching branches: "+(0,g.getErrorMessage)(n)}}}catch(n){return o.warn("Overall error in ensureCorrectBranch",{requestId:e,taskId:t,filePath:r,error:(0,g.getErrorMessage)(n)}),s.incrementCounter(i+"_branch_switch_overall_error",1),{switched:!1,message:"Branch switching error: "+(0,g.getErrorMessage)(n)}}},exports.autoSwitchToRequestBranch=o,exports.determineExpectedBranch=function(e,t,r){try{return t.currentRequestId?(r.debug("Worktree should be on correct branch",{taskId:e,requestId:t.currentRequestId}),null):null}catch(t){return r.warn("Failed to determine expected branch for task",{taskId:e,error:(0,g.getErrorMessage)(t)}),null}},exports.validateWorkspaceContextForFileOperation=s,exports.ensureCorrectWorkspaceContext=async function(e){const{taskPromoted:t,requestId:r,context:n,operation:i,logger:a,metrics:c,metricsPrefix:l,requireRequestContext:u=!0}=e
|
|
4323
4193
|
try{const e=await o(0,r,n,a,c,l)
|
|
4324
4194
|
if(e.switched&&a.info(`Auto-switched to request workspace during ${i} operation`,{requestId:r,branchName:e.branchName,message:e.message,taskPromoted:t,operation:i}),u&&r){const t=s(n,r,i,a)
|
|
4325
4195
|
if(!t.isValid)return a.error("Workspace context validation failed for "+i,{requestId:r,operation:i,error:t.errorMessage}),{success:!1,switched:e.switched,branchName:e.branchName,error:t.errorMessage,lockAcquired:e.lockAcquired,lockedRequestId:e.lockedRequestId}}return a.debug("Workspace context successfully ensured for "+i,{requestId:r,operation:i,switched:e.switched,branchName:e.branchName}),{success:!0,switched:e.switched,branchName:e.branchName,lockAcquired:e.lockAcquired,lockedRequestId:e.lockedRequestId}}catch(e){const t=(0,g.getErrorMessage)(e)
|
|
@@ -4517,10 +4387,10 @@ if(s.workspaceManager){const t=s.workspaceManager.getCurrentContext()
|
|
|
4517
4387
|
if("multi-agent"===t.mode&&t.requestId){if(!t.basePath.includes("/worktrees/")&&!t.basePath.includes("\\worktrees\\"))throw i.error("CRITICAL BUG: Multi-agent mode but basePath is not a worktree path",{taskId:e,requestId:t.requestId,basePath:t.basePath,expectedPattern:"should contain /worktrees/ or \\worktrees\\",issue:"workspace_context_incorrect"}),Error(`Multi-agent mode context error: basePath '${t.basePath}' is not a worktree path. This will cause commits to go to main branch instead of the request branch.`)
|
|
4518
4388
|
f=(0,a.simpleGit)(t.basePath),i.debug("Using WorkspaceManager git instance for commit",{taskId:e,mode:t.mode,requestId:t.requestId,basePath:t.basePath,branchName:t.branchName,worktreeValidated:!0})}}if(f){i.info("commitToGit called with:",{taskId:e,recordId:r,localRecordId:n,hasLocalRecordId:!!n,localRecordIdType:typeof n,normalizedPath:t})
|
|
4519
4389
|
let a=!1,m=""
|
|
4520
|
-
try{if(m=(await f.raw(["rev-parse","--show-toplevel"])).trim(),a=m.includes("/worktrees/")||m.includes("\\worktrees\\"),i.info("Git context detection for commit operation:",{taskId:e,gitRepoPath:m,isWorktreeOperation:a,
|
|
4521
|
-
i.info("Git repository status before commit:",{taskId:e,currentBranch:r.trim(),currentCommit:n.trim().substring(0,8),repoPath:o.trim(),targetFile:t,
|
|
4390
|
+
try{if(m=(await f.raw(["rev-parse","--show-toplevel"])).trim(),a=m.includes("/worktrees/")||m.includes("\\worktrees\\"),i.info("Git context detection for commit operation:",{taskId:e,gitRepoPath:m,isWorktreeOperation:a,targetFile:t,expectedContext:"worktree"}),!a)throw i.error("CRITICAL: Multi-agent operation using main repo Git instead of worktree",{taskId:e,detectedPath:m,targetFile:t,currentRequestId:s.getCurrentRequestId?s.getCurrentRequestId():"unknown"}),Error(`Git context mismatch: Multi-agent operation attempted to commit ${t} using main repository Git instance at ${m}, but should use worktree Git instance. This will fail due to .gitignore rules.`)}catch(e){i.warn("Failed to get Git instance info:",{error:e instanceof Error?e.message:e+""})}try{const r=await f.revparse(["--abbrev-ref","HEAD"]),n=await f.revparse(["HEAD"]),o=await f.revparse(["--show-toplevel"])
|
|
4391
|
+
i.info("Git repository status before commit:",{taskId:e,currentBranch:r.trim(),currentCommit:n.trim().substring(0,8),repoPath:o.trim(),targetFile:t,currentRequestId:s.getCurrentRequestId?s.getCurrentRequestId():"none"})
|
|
4522
4392
|
const a=r.trim(),c=s.getCurrentRequestId?s.getCurrentRequestId():null
|
|
4523
|
-
if(
|
|
4393
|
+
if(c){const t="requests/"+c
|
|
4524
4394
|
a!=="requests/"+c?i.warn("Multi-agent file operation may be on wrong branch",{taskId:e,actualBranch:a,expectedPattern:t,requestId:c}):i.info("Multi-agent file operation on expected branch",{taskId:e,branchName:a,requestId:c})}}catch(e){i.warn("Failed to get Git status before commit:",{error:e instanceof Error?e.message:e+""})}try{if(f){const r=await f.revparse(["HEAD"])
|
|
4525
4395
|
p=await(0,l.findPreviousCommit)(f,t,r),i.info(`Previous commit hash for ${t}: ${p||"none (new file)"}`,{taskId:e,gitInstancePath:m||"unknown",isWorktreeOperation:a,usingCorrectGitInstance:!0})}else i.warn("Git not available for previous commit detection: "+t,{taskId:e,reason:"no_git_instance"})}catch(e){i.warn(`Failed to find previous commit for ${t}:`,{error:(0,u.getErrorMessage)(e)})}const y=n?`[RECORD:${n}] ${o}`:o
|
|
4526
4396
|
await f.add(t),g=(await f.commit(y)).commit
|
|
@@ -4533,25 +4403,19 @@ function t(){const e=process.argv[1]||""
|
|
|
4533
4403
|
if(e.includes("/dist-dev/")||e.includes("\\dist-dev\\"))return!0
|
|
4534
4404
|
if(e.includes("/dist/")||e.includes("\\dist\\"))return!1
|
|
4535
4405
|
const t=process.cwd()
|
|
4536
|
-
return!(!t.includes("/dist-dev")&&!t.includes("\\dist-dev"))}Object.defineProperty(exports,"__esModule",{value:!0}),exports.isDevBuild=t,exports.getBuildMode=function(){return t()?"development":"production"},exports.enableDebugMode=function(){return"true"===process.env.ENABLE_DEBUG_TOOLS&&(process.env.DEBUG_LOGGING="true",!0)}},
|
|
4537
|
-
Object.defineProperty(exports,"__esModule",{value:!0}),exports.
|
|
4538
|
-
|
|
4539
|
-
|
|
4540
|
-
|
|
4541
|
-
const r=t(3444).defaultLogger.child({component:"client-info-utils"})},8035(e,exports,t){"use strict"
|
|
4542
|
-
function r(e,t,r){try{const n=`[${(new Date).toISOString()}] [detached-subagent] ${t}${r?" "+JSON.stringify(r):""}\n`,o=(0,a.join)(e||process.cwd(),".alchemy_lab","spawn-debug.log");(0,i.appendFileSync)(o,n)}catch{}}function n(e){const{agent:t,prompt:n,cwd:l,parentServerUrl:u,parentSessionId:d,sessionId:h,model:g,initialBranch:p,serverUrl:f,onSpawn:m,onError:y}=e
|
|
4543
|
-
try{const s={...process.env}
|
|
4544
|
-
u&&(s.OPENCODE_PARENT_SERVER=u),p&&(s.ALCHEMY_INITIAL_BRANCH=p),e.allowParallel&&(s.ALCHEMY_ALLOW_PARALLEL="1")
|
|
4545
|
-
const d=new Date,y=`${(d.getHours()+"").padStart(2,"0")}${(d.getMinutes()+"").padStart(2,"0")}${(d.getSeconds()+"").padStart(2,"0")}`,w=Math.random().toString(36).substring(2,7)
|
|
4406
|
+
return!(!t.includes("/dist-dev")&&!t.includes("\\dist-dev"))}Object.defineProperty(exports,"__esModule",{value:!0}),exports.isDevBuild=t,exports.getBuildMode=function(){return t()?"development":"production"},exports.enableDebugMode=function(){return"true"===process.env.ENABLE_DEBUG_TOOLS&&(process.env.DEBUG_LOGGING="true",!0)}},8035(e,exports,t){"use strict"
|
|
4407
|
+
function r(e,t,r){try{const n=`[${(new Date).toISOString()}] [detached-subagent] ${t}${r?" "+JSON.stringify(r):""}\n`,o=(0,i.join)(e||process.cwd(),".alchemy_lab","spawn-debug.log");(0,s.appendFileSync)(o,n)}catch{}}Object.defineProperty(exports,"__esModule",{value:!0}),exports.spawnDetachedSubagent=function(e){const{agent:t,prompt:c,cwd:l,sessionId:u,model:d,initialBranch:h,serverUrl:g,onSpawn:p}=e
|
|
4408
|
+
try{const o={...process.env},f=l||process.cwd()
|
|
4409
|
+
o.OPENCODE_DATA_DIR=(0,i.join)(f,".alchemy_lab","opencode"),h&&(o.ALCHEMY_INITIAL_BRANCH=h),e.allowParallel&&(o.ALCHEMY_ALLOW_PARALLEL="1")
|
|
4410
|
+
const m=new Date,y=`${(m.getHours()+"").padStart(2,"0")}${(m.getMinutes()+"").padStart(2,"0")}${(m.getSeconds()+"").padStart(2,"0")}`,w=Math.random().toString(36).substring(2,7)
|
|
4546
4411
|
let k
|
|
4547
|
-
if(
|
|
4548
|
-
e>0?k.splice(e,0,"--model",
|
|
4549
|
-
const b=(0,
|
|
4412
|
+
if(o.ALCHEMY_SESSION_TAG=`mcp-${y}-${w}`,r(l,"Spawn env setup",{agent:t,initialBranch:h||"none",sessionId:u||"new",attachMode:!!g}),k=g&&u&&c?["run","--attach",g,"--session",u,"--agent",t,c]:u&&c?["run","--session",u,"--agent",t,c]:c?["run","--agent",t,c]:["run","--agent",t],d){const e=k.findIndex((e=>e===c))
|
|
4413
|
+
e>0?k.splice(e,0,"--model",d):k.push("--model",d)}r(l,"Spawning opencode",{args:k.map((e=>e===c?`[prompt:${e.length}chars]`:e)),model:d||"not specified",promptLength:c?.length,promptPreview:c?.slice(0,100),cwd:l,hasSessionId:!!u})
|
|
4414
|
+
const b=(0,i.join)(l||process.cwd(),".alchemy_lab"),I=(0,i.join)(b,"spawn-stderr.log")
|
|
4550
4415
|
let v
|
|
4551
|
-
try{v=(0,
|
|
4552
|
-
return _.unref(),
|
|
4553
|
-
|
|
4554
|
-
const o=t(5317),s=t(8824),i=t(9896),a=t(6928),c=t(9068)},8037(e,exports,t){"use strict"
|
|
4416
|
+
try{v=(0,s.openSync)(I,"a")}catch{}const C=(0,a.resolveRunCommand)(),_=(0,n.spawn)(C.command,[...C.prependArgs,...k],{detached:!0,stdio:["ignore","ignore",v??"ignore"],cwd:l||process.cwd(),env:o})
|
|
4417
|
+
return _.unref(),p&&p(_.pid),{success:!0,pid:_.pid}}catch(e){return{success:!1,error:(0,o.getErrorMessage)(e)}}}
|
|
4418
|
+
const n=t(5317),o=t(8824),s=t(9896),i=t(6928),a=t(9068)},8037(e,exports,t){"use strict"
|
|
4555
4419
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.handleListRequests=async function(e,t,i,a,c){const l=a.child({tool:"list_requests"}),u=c.startTimer("tool_execution_time")
|
|
4556
4420
|
try{const{filters:s={}}=e,a=["open","in_progress","ready_for_review","completed","canceled","reverted"]
|
|
4557
4421
|
if(s.status&&!a.includes(s.status))throw new r.ValidationError(`Invalid status: ${s.status}. Must be one of: ${a.join(", ")}`)
|
|
@@ -4566,17 +4430,15 @@ const h=i.getRequestClient(),g=await h.listRequests(d)
|
|
|
4566
4430
|
if(l.debug("=== RAW SERVER RESPONSE DEBUG ===",{responseType:typeof g,isArray:Array.isArray(g),responseKeys:g?Object.keys(g):[],fullResponse:JSON.stringify(g,null,2)}),g&&"object"==typeof g&&"data"in g){const e=g.data
|
|
4567
4431
|
l.debug("=== SERVER RESPONSE DATA SECTION ===",{dataType:typeof e,isDataArray:Array.isArray(e),dataLength:Array.isArray(e)?e.length:"not array",firstItemKeys:Array.isArray(e)&&e.length>0?Object.keys(e[0]):"no items",firstItemSample:Array.isArray(e)&&e.length>0?JSON.stringify(e[0],null,2):"no items"}),Array.isArray(e)&&e.length>0&&e.slice(0,3).forEach(((e,t)=>{l.info(`=== ITEM ${t+1} LOCK INFO CHECK ===`,{id:e.id,hasLockInfo:"lockInfo"in e,lockInfoValue:e.lockInfo,allKeys:Object.keys(e),lockRelatedKeys:Object.keys(e).filter((e=>e.toLowerCase().includes("lock")))})}))}l.debug("Raw requests response data",{responseData:JSON.stringify(g)}),l.debug("Requests response structure",{type:typeof g,isArray:Array.isArray(g),hasData:null!=g,properties:g?Object.keys(g):[],dataPreview:g?JSON.stringify(g).substring(0,200)+"...":"null"}),l.debug("=== BEFORE EXTRACTION ===",{responseHasData:g&&"data"in g,responseDataLength:g&&"data"in g&&Array.isArray(g.data)?g.data.length:"not array",firstItemBeforeExtraction:g&&"data"in g&&Array.isArray(g.data)&&g.data.length>0?{id:g.data[0].id,hasLockInfo:"lockInfo"in g.data[0],lockInfo:g.data[0].lockInfo,allKeys:Object.keys(g.data[0])}:"no data"})
|
|
4568
4432
|
const p=(0,n.extractArrayFromResponse)(g,{logger:l,operationName:"listRequests",defaultValue:[]})
|
|
4569
|
-
l.info("=== AFTER EXTRACTION ===",{extractedCount:p.length,firstItemAfterExtraction:p.length>0?{id:p[0].id,hasLockInfo:"lockInfo"in p[0],lockInfo:p[0].lockInfo,allKeys:Object.keys(p[0])}:"no items"}),l.info(`Extracted ${p.length} requests from response`)
|
|
4570
|
-
|
|
4571
|
-
|
|
4572
|
-
|
|
4573
|
-
const m=p.map((e=>{let t=""
|
|
4574
|
-
if(l.info(`=== FORMATTING REQUEST ${e.id} ===`,{multiAgentMode:f,hasLockInfo:!!e.lockInfo,lockInfoValue:e.lockInfo,willShowLockInfo:!!e.lockInfo,note:"Lock info displayed when available regardless of mode"}),e.lockInfo){if(l.debug(`Processing lock info for ${e.id}:`,e.lockInfo),e.lockInfo.isLocked&&!e.lockInfo.isExpired){const{sessionTag:r}=(0,o.getGlobalClientInfo)(),n=e.lockInfo.lockedBySessionTag||"unknown"
|
|
4433
|
+
if(l.info("=== AFTER EXTRACTION ===",{extractedCount:p.length,firstItemAfterExtraction:p.length>0?{id:p[0].id,hasLockInfo:"lockInfo"in p[0],lockInfo:p[0].lockInfo,allKeys:Object.keys(p[0])}:"no items"}),l.info(`Extracted ${p.length} requests from response`),l.debug("Lock info analysis",{requestCount:p.length,firstRequestSample:p.length>0?{id:p[0].id,hasLockInfo:!!p[0].lockInfo,lockInfo:p[0].lockInfo,allProperties:Object.keys(p[0])}:"No requests to sample"}),p.length>0&&p.forEach(((e,t)=>{l.debug(`Request ${t+1} lock debug`,{id:e.id,title:e.title?.substring(0,50)+"...",hasLockInfo:!!e.lockInfo,lockInfoDetails:e.lockInfo||"NO LOCK INFO",allKeys:Object.keys(e).filter((e=>e.includes("lock")||e.includes("Lock")))})})),0===p.length)return u({success:!0,requestCount:0}),{content:[{type:"text",text:"No requests found with the specified filters."}]}
|
|
4434
|
+
l.info("=== PRE-DISPLAY REQUEST ANALYSIS ===",{totalRequests:p.length}),p.forEach(((e,t)=>{l.info(`=== REQUEST ${t+1}/${p.length} PRE-DISPLAY ANALYSIS ===`,{id:e.id,title:e.title?.substring(0,30)+"...",hasLockInfo:"lockInfo"in e,lockInfoType:typeof e.lockInfo,lockInfoValue:e.lockInfo,lockInfoIsNull:null===e.lockInfo,lockInfoIsUndefined:void 0===e.lockInfo,allProperties:Object.keys(e),lockRelatedProperties:Object.keys(e).filter((e=>e.toLowerCase().includes("lock")||e.toLowerCase().includes("session")||e.toLowerCase().includes("expire")))}),e.lockInfo&&l.info(`=== REQUEST ${e.id} LOCK INFO DEEP DIVE ===`,{lockInfoKeys:Object.keys(e.lockInfo),isLocked:e.lockInfo.isLocked,lockedBySessionTag:e.lockInfo.lockedBySessionTag,timeRemainingFormatted:e.lockInfo.timeRemainingFormatted,isExpired:e.lockInfo.isExpired,fullLockInfo:JSON.stringify(e.lockInfo,null,2)})}))
|
|
4435
|
+
const f=p.map((e=>{let t=""
|
|
4436
|
+
if(l.info(`=== FORMATTING REQUEST ${e.id} ===`,{hasLockInfo:!!e.lockInfo,lockInfoValue:e.lockInfo,willShowLockInfo:!!e.lockInfo,note:"Lock info displayed when available regardless of mode"}),e.lockInfo){if(l.debug(`Processing lock info for ${e.id}:`,e.lockInfo),e.lockInfo.isLocked&&!e.lockInfo.isExpired){const{sessionTag:r}=(0,o.getGlobalClientInfo)(),n=e.lockInfo.lockedBySessionTag||"unknown"
|
|
4575
4437
|
t=n===r?` [LOCKED by me, expires in ${e.lockInfo.timeRemainingFormatted}]`:` [LOCKED by ${n.length>20?n.substring(0,17)+"...":n}, expires in ${e.lockInfo.timeRemainingFormatted}]`}else t=" [AVAILABLE]"
|
|
4576
4438
|
l.debug(`Generated lock info for ${e.id}: "${t}"`)}else l.debug("No lock info available for "+e.id)
|
|
4577
|
-
return`**${e.title}** (${e.id}) [${e.type}]${t}\nStatus: ${e.status}\nType: ${e.type}\nCreated: ${new Date(e.createdAt).toLocaleString()}\nUpdated: ${new Date(e.updatedAt).toLocaleString()}\n`})).join("\n---\n"),
|
|
4578
|
-
let
|
|
4579
|
-
return
|
|
4439
|
+
return`**${e.title}** (${e.id}) [${e.type}]${t}\nStatus: ${e.status}\nType: ${e.type}\nCreated: ${new Date(e.createdAt).toLocaleString()}\nUpdated: ${new Date(e.updatedAt).toLocaleString()}\n`})).join("\n---\n"),m=p.some((e=>e.lockInfo))
|
|
4440
|
+
let y=`Found ${p.length} request${1===p.length?"":"s"}:`
|
|
4441
|
+
return m&&(y+="\n\n**Lock Status:**\n",y+="LOCKED = Locked by an agent (shows session name and expiration)\n",y+="AVAILABLE = Not currently locked, safe to work on\n"),u({success:!0,requestCount:p.length}),{content:[{type:"text",text:`${y}\n\n${f}`}]}}catch(t){return l.error("Error listing requests",{args:e,error:t instanceof Error?t.stack:t+""}),u({success:!1,error:t instanceof Error?t.name:"unknown"}),{content:[{type:"text",text:"Error listing requests: "+(0,s.getErrorMessage)(t)}],isError:!0}}}
|
|
4580
4442
|
const r=t(9860),n=t(2960),o=t(5172),s=t(8824)},8045(e,exports,t){"use strict"
|
|
4581
4443
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.def=void 0
|
|
4582
4444
|
const r=t(6183),n=t(7456)
|
|
@@ -4619,14 +4481,14 @@ const S=await u.ensureCorrectWorkspaceContext({taskPromoted:q.taskPromoted,reque
|
|
|
4619
4481
|
if(!S.success){if(S.isLockConflict)return{content:[{type:"text",text:"\u274c "+S.error}],isError:!0}
|
|
4620
4482
|
throw Error(S.error)}let T=!1
|
|
4621
4483
|
try{T=(await a.default.stat(v)).isDirectory()}catch{T=!1}k=u.FileOperationPhase.RECORD_CREATION,i.incrementCounter("create_directory_phase",1,{phase:k})
|
|
4622
|
-
const{toolRecordId:
|
|
4623
|
-
y=
|
|
4624
|
-
let
|
|
4484
|
+
const{toolRecordId:R,localToolRecordId:P}=await u.createFileOperationRecords(d,_,t.projectId,b.recordType,I,{directoryExists:T,userComment:g},r,n,f,i,b.metricsPrefix,p)
|
|
4485
|
+
y=R,w=R,k=b.fileOperationPhase,i.incrementCounter("create_directory_phase",1,{phase:k})
|
|
4486
|
+
let M=T
|
|
4625
4487
|
if(!T){await a.default.mkdir(v,{recursive:!0}),f.info("Successfully created directory "+I)
|
|
4626
4488
|
try{const e=c.default.join(v,".gitkeep")
|
|
4627
|
-
await a.default.writeFile(e,"# This file makes the directory trackable by Git\n"),
|
|
4489
|
+
await a.default.writeFile(e,"# This file makes the directory trackable by Git\n"),M=!0,f.info("Created .gitkeep file for Git tracking")}catch(e){f.warn("Failed to create .gitkeep file",{error:e instanceof Error?e.message:e+""}),M=!1}}const x=Date.now()-m
|
|
4628
4490
|
i.recordValue("create_directory_time",x),i.incrementCounter("create_directory_success",1),k=u.FileOperationPhase.GIT_COMMIT,i.incrementCounter("create_directory_phase",1,{phase:k})
|
|
4629
|
-
const
|
|
4491
|
+
const j=`Create directory: ${I} - ${g||"Create directory"}`,O=!T&&M?I+"/.gitkeep":I,$=await u.commitToGit(d,O,R,P,j,t,f,i,b.metricsPrefix)
|
|
4630
4492
|
k=u.FileOperationPhase.RECORD_UPDATE_SUCCESS,i.incrementCounter("create_directory_phase",1,{phase:k}),await u.updateFileOperationRecords(d,y,w,I,b.recordType,`Successfully ${T?"verified":"created"} directory: ${I}`,{status:"completed",commitHash:$.commitHash,previousCommitHash:$.previousCommitHash,directoryExists:T,isDirectory:!0,userComment:g},`Successfully ${T?"verified":"created"} directory: ${I}`,r,n,f,i,b.metricsPrefix)
|
|
4631
4493
|
const D=t.getCurrentBranchContext?await t.getCurrentBranchContext():{branch:null,requestId:null,isMain:!0}
|
|
4632
4494
|
return{content:[{type:"text",text:T?"Directory already exists":`Successfully created directory${$.commitHash?"\nCommit: "+$.commitHash.substring(0,8):""}${D.requestId?"\nBranch: "+D.requestId:""}${S.lockAcquired&&S.lockedRequestId?"\n\u{1f512} **Locked request:** "+S.lockedRequestId:""}`}]}}catch(o){if(e.taskId&&n)try{const r=o instanceof d.NotFoundError||o instanceof d.ValidationError||o instanceof h.ZodError
|
|
@@ -4706,31 +4568,25 @@ let o=`## Plans (${r.length})\n\n`
|
|
|
4706
4568
|
for(const e of r){const t=e.localId||e.id,r=new Date(e.updatedAt).toLocaleString(),n=e.content?e.content.substring(0,120).replace(/\n/g," ").trim()+(e.content.length>120?"...":""):""
|
|
4707
4569
|
o+=`**${t}** \u2014 ${e.filename}\n`,o+=` Updated: ${r}\n`,n&&(o+=` ${n}\n`),o+="\n"}return{content:[{type:"text",text:o}]}}catch(e){return s.error("Failed to list plans",{error:(0,r.getErrorMessage)(e)}),{content:[{type:"text",text:"\u274c **Failed to list plans:** "+(0,r.getErrorMessage)(e)}],isError:!0}}}
|
|
4708
4570
|
const r=t(8824)},8411(e,exports,t){"use strict"
|
|
4709
|
-
function r(e){
|
|
4710
|
-
|
|
4571
|
+
function r(e,t,r,o){try{const i={mode:"multi-agent",created:o,hostname:a.default.hostname()}
|
|
4572
|
+
s.default.writeFileSync(e,JSON.stringify(i,null,2))
|
|
4573
|
+
const c={count:1,processes:[{pid:r,started:o}]}
|
|
4574
|
+
return s.default.writeFileSync(t,JSON.stringify(c,null,2)),n(e,t,r),h.info("Created new lock",{mode:i.mode,pid:r}),!0}catch(e){return h.error("Error creating new lock",{error:(0,u.getErrorMessage)(e)}),!1}}function n(e,t,r){["SIGINT","SIGTERM","exit"].forEach((n=>{process.on(n,(()=>{try{if(s.default.existsSync(t)){const o=s.default.readFileSync(t,"utf8"),i=JSON.parse(o)
|
|
4575
|
+
i.processes=i.processes.filter((e=>e.pid!==r)),i.count=i.processes.length,i.count>0?(s.default.writeFileSync(t,JSON.stringify(i,null,2)),h.debug("Removed process from multi-agent references",{signal:n,pid:r,remaining:i.count})):(s.default.unlinkSync(t),s.default.existsSync(e)&&s.default.unlinkSync(e),h.debug("Removed multi-agent lock files (last process)",{signal:n,pid:r}))}}catch(e){h.error("Error removing multi-agent lock files",{error:e instanceof Error?e.message:e+"",signal:n})}"exit"!==n&&process.exit(0)}))}))}var o=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}}
|
|
4576
|
+
Object.defineProperty(exports,"__esModule",{value:!0}),exports.acquireProcessLock=function(e){const t=i.default.join(e,c.ALCHEMY_DIR_NAME)
|
|
4577
|
+
let o,l
|
|
4578
|
+
try{s.default.existsSync(t)||(s.default.mkdirSync(t,{recursive:!0}),h.debug(`Created ${c.ALCHEMY_DIR_NAME} directory for lock file`,{alchemyLabDir:t})),o=i.default.join(t,".mcp-server.lock"),l=i.default.join(t,".mcp-agents.refs"),h.debug(`Using ${c.ALCHEMY_DIR_NAME} directory for lock files`,{lockFilePath:o,refsFilePath:l})}catch(r){h.error(`Failed to create ${c.ALCHEMY_DIR_NAME} directory`,{alchemyLabDir:t,error:r instanceof Error?r.message:r+""}),o=i.default.join(e,".mcp-server.lock"),l=i.default.join(e,".mcp-agents.refs"),h.warn("Falling back to base directory for lock files",{lockFilePath:o,refsFilePath:l})}const g=process.pid,p=(new Date).toISOString()
|
|
4579
|
+
try{const e=function(e){if(!s.default.existsSync(e))return null
|
|
4580
|
+
try{const t=s.default.readFileSync(e,"utf8").trim()
|
|
4711
4581
|
try{const e=JSON.parse(t)
|
|
4712
|
-
return
|
|
4713
|
-
|
|
4714
|
-
|
|
4715
|
-
|
|
4716
|
-
|
|
4717
|
-
|
|
4718
|
-
o
|
|
4719
|
-
|
|
4720
|
-
s.processes=s.processes.filter((e=>e.pid!==r)),s.count=s.processes.length,s.count>0?(a.default.writeFileSync(t,JSON.stringify(s,null,2)),p.debug("Removed process from multi-agent references",{signal:n,pid:r,remaining:s.count})):(a.default.unlinkSync(t),a.default.existsSync(e)&&a.default.unlinkSync(e),p.debug("Removed multi-agent lock files (last process)",{signal:n,pid:r}))}}catch(e){p.error("Error removing multi-agent lock files",{error:e instanceof Error?e.message:e+"",signal:n})}"exit"!==n&&process.exit(0)}))}))}var i=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}}
|
|
4721
|
-
Object.defineProperty(exports,"__esModule",{value:!0}),exports.acquireProcessLock=function(e,t=!1){const i=c.default.join(e,u.ALCHEMY_DIR_NAME)
|
|
4722
|
-
let d,f
|
|
4723
|
-
try{a.default.existsSync(i)||(a.default.mkdirSync(i,{recursive:!0}),p.debug(`Created ${u.ALCHEMY_DIR_NAME} directory for lock file`,{alchemyLabDir:i})),d=c.default.join(i,".mcp-server.lock"),f=c.default.join(i,".mcp-agents.refs"),p.debug(`Using ${u.ALCHEMY_DIR_NAME} directory for lock files`,{lockFilePath:d,refsFilePath:f})}catch(t){p.error(`Failed to create ${u.ALCHEMY_DIR_NAME} directory`,{alchemyLabDir:i,error:t instanceof Error?t.message:t+""}),d=c.default.join(e,".mcp-server.lock"),f=c.default.join(e,".mcp-agents.refs"),p.warn("Falling back to base directory for lock files",{lockFilePath:d,refsFilePath:f})}const m=process.pid,y=(new Date).toISOString()
|
|
4724
|
-
try{const e=r(d)
|
|
4725
|
-
if(p.info("Lock acquisition attempt",{pid:m,multiAgentMode:t,lockFilePath:d,lockExists:!!e,lockData:e?{mode:e.mode,pid:e.pid,hostname:e.hostname,created:e.created}:null}),!e)return p.info("No existing lock - creating new lock",{pid:m,mode:t?"multi-agent":"single-agent"}),o(d,f,m,y,t)
|
|
4726
|
-
{const r=Date.now()-new Date(e.created).getTime(),i=r>g,c=l.default.hostname(),u=e.hostname!==c&&"unknown"!==e.hostname
|
|
4727
|
-
if(i)return p.warn("\u26a0\ufe0f Clearing stale lock (older than 24 hours)",{lockAge:Math.round(r/1e3/60/60)+" hours",lockCreated:e.created,lockHostname:e.hostname}),o(d,f,m,y,t)
|
|
4728
|
-
if(u)return p.warn("\u26a0\ufe0f Clearing lock from different machine",{lockHostname:e.hostname,currentHostname:c}),o(d,f,m,y,t)
|
|
4729
|
-
if("single-agent"===e.mode)return e.pid===m?(p.debug("Same process already has lock",{pid:m}),!0):n(e.pid)?(p.warn("Cannot acquire lock - single-agent mode active",{existingPid:e.pid,currentPid:m,requestedMode:t?"multi-agent":"single-agent"}),!1):(p.info("Taking over lock from dead single-agent process",{deadPid:e.pid,currentPid:m,newMode:t?"multi-agent":"single-agent"}),o(d,f,m,y,t))
|
|
4730
|
-
if("multi-agent"===e.mode)return t?function(e,t,r){try{let o={count:0,processes:[]}
|
|
4731
|
-
if(a.default.existsSync(e)){const t=a.default.readFileSync(e,"utf8")
|
|
4732
|
-
o=JSON.parse(t),o.processes=o.processes.filter((e=>n(e.pid))),o.count=o.processes.length}return o.processes.push({pid:t,started:r}),o.count=o.processes.length,a.default.writeFileSync(e,JSON.stringify(o,null,2)),s(e.replace(".mcp-agents.refs",".mcp-server.lock"),e,t),p.info("Joined multi-agent lock",{pid:t,totalAgents:o.count}),!0}catch(e){return p.error("Error joining multi-agent lock",{error:(0,h.getErrorMessage)(e)}),!1}}(f,m,y):(p.warn("Cannot acquire lock - multi-agent mode active",{currentPid:m,requestedMode:"single-agent"}),!1)}return!1}catch(e){return p.error("Error acquiring lock",{error:(0,h.getErrorMessage)(e),pid:m}),!1}}
|
|
4733
|
-
const a=i(t(9896)),c=i(t(6928)),l=i(t(857)),u=t(4139),d=t(3444),h=t(8824),g=864e5,p=(0,d.createLogger)({serviceName:"process-lock",level:d.LogLevel.DEBUG,logToFile:!1})},8451(e,exports,t){"use strict"
|
|
4582
|
+
return h.debug("Read JSON lock data",e),e}catch{if(isNaN(parseInt(t,10)))return h.warn("Invalid lock file content",{content:t}),null
|
|
4583
|
+
const e={mode:"multi-agent",created:(new Date).toISOString(),hostname:"unknown"}
|
|
4584
|
+
return h.debug("Read legacy PID lock data",e),e}}catch(e){return h.error("Error reading lock file",{error:(0,u.getErrorMessage)(e)}),null}}(o)
|
|
4585
|
+
if(h.info("Lock acquisition attempt",{pid:g,lockFilePath:o,lockExists:!!e,lockData:e?{mode:e.mode,hostname:e.hostname,created:e.created}:null}),e){const t=Date.now()-new Date(e.created).getTime(),i=t>d,c=a.default.hostname(),f=e.hostname!==c&&"unknown"!==e.hostname
|
|
4586
|
+
return i?(h.warn("\u26a0\ufe0f Clearing stale lock (older than 24 hours)",{lockAge:Math.round(t/1e3/60/60)+" hours",lockCreated:e.created,lockHostname:e.hostname}),r(o,l,g,p)):f?(h.warn("\u26a0\ufe0f Clearing lock from different machine",{lockHostname:e.hostname,currentHostname:c}),r(o,l,g,p)):"multi-agent"===e.mode?function(e,t,r){try{let o={count:0,processes:[]}
|
|
4587
|
+
if(s.default.existsSync(e)){const t=s.default.readFileSync(e,"utf8")
|
|
4588
|
+
o=JSON.parse(t),o.processes=o.processes.filter((e=>function(e){try{return process.kill(e,0),!0}catch{return!1}}(e.pid))),o.count=o.processes.length}return o.processes.push({pid:t,started:r}),o.count=o.processes.length,s.default.writeFileSync(e,JSON.stringify(o,null,2)),n(e.replace(".mcp-agents.refs",".mcp-server.lock"),e,t),h.info("Joined multi-agent lock",{pid:t,totalAgents:o.count}),!0}catch(e){return h.error("Error joining multi-agent lock",{error:(0,u.getErrorMessage)(e)}),!1}}(l,g,p):(h.info("Taking over legacy lock",{currentPid:g,oldMode:e.mode}),r(o,l,g,p))}return h.info("No existing lock - creating new lock",{pid:g,mode:"multi-agent"}),r(o,l,g,p)}catch(e){return h.error("Error acquiring lock",{error:(0,u.getErrorMessage)(e),pid:g}),!1}}
|
|
4589
|
+
const s=o(t(9896)),i=o(t(6928)),a=o(t(857)),c=t(4139),l=t(3444),u=t(8824),d=864e5,h=(0,l.createLogger)({serviceName:"process-lock",level:l.LogLevel.DEBUG,logToFile:!1})},8451(e,exports,t){"use strict"
|
|
4734
4590
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.formatFileSize=function(e){return 1024>e?e+" bytes":1048576>e?(e/1024).toFixed(2)+" KB":1073741824>e?(e/1048576).toFixed(2)+" MB":(e/1073741824).toFixed(2)+" GB"},exports.truncate=function(e,t){return e.length>t?e.substring(0,t-3)+"...":e},exports.escapeRegExp=function(e){return e.replace(/[.*+?^${}()|[\]\\]/g,"\\$&")},exports.countOccurrences=function(e,t){if(0===t.length)return 0
|
|
4735
4591
|
let r=0,n=0
|
|
4736
4592
|
for(;n=e.indexOf(t,n),-1!==n;)r++,n+=t.length
|
|
@@ -4912,62 +4768,13 @@ const r=await e.proxyGet("/api/agents/templates")
|
|
|
4912
4768
|
r&&Array.isArray(r)&&r.length>0?(s=r.map((e=>({id:e.id||e.name,name:e.name,description:e.description,mode:e.mode,builtIn:e.builtIn}))),t.info("Agent registry initialized",{agentCount:s.length})):(t.warn("No agents returned from API, using defaults"),s=n),i=!0}catch(e){t.warn("Failed to fetch agents from API, using defaults",{error:e instanceof Error?e.message:e+""}),s=n,i=!0}})(),a)},exports.getAvailableAgents=t,exports.getAgentNames=r,exports.isValidAgent=function(e){return r().includes(e)},exports.getDefaultAgent=function(){return"work"},exports.formatAgentsForDescription=function(){return t().map((e=>`'${e.name}'${e.description?" - "+e.description:""}`)).join(", ")},exports.isAgentRegistryInitialized=function(){return i},exports.getBuiltInAgentConfig=function(e){const t=n.find((t=>t.name===e))
|
|
4913
4769
|
return t?{preferredProvider:t.preferredProvider||"inherit",preferredModelTier:t.preferredModelTier||"same",requestContextMode:t.requestContextMode}:null},exports.getAllowedSubagents=function(e){return o[e]||null},exports.resetAgentRegistry=function(){s=null,i=!1,a=null}
|
|
4914
4770
|
const n=[{id:"coder",name:"coder",description:"Development and implementation agent",builtIn:!0,preferredModelTier:"same",requestContextMode:"required"},{id:"research",name:"research",description:"Codebase research and exploration agent",builtIn:!0,preferredModelTier:"two_down",requestContextMode:"none"},{id:"journal",name:"journal",description:"Journal generation agent",builtIn:!0,preferredModelTier:"one_down"},{id:"planner",name:"planner",description:"Planning and architecture agent",builtIn:!0,preferredModelTier:"same"},{id:"specialist",name:"specialist",description:"Domain specialist for development tasks",builtIn:!0,preferredModelTier:"same"},{id:"auto-planner",name:"auto-planner",description:"Autonomous background planner",builtIn:!0,preferredModelTier:"same"},{id:"alchemist",name:"alchemist",description:"Persistent orchestrator",builtIn:!0,preferredModelTier:"same"}],o={alchemist:["specialist","research","planner"],specialist:["coder","research","auto-planner","planner"],tester:["research"],"auto-tester":["research"]}
|
|
4915
|
-
let s=null,i=!1,a=null},
|
|
4916
|
-
Object.defineProperty(exports,"__esModule",{value:!0}),exports.BranchGitAdapter=void 0
|
|
4917
|
-
const r=t(7225),n=t(7075),o=t(7478),s=t(8824)
|
|
4918
|
-
exports.BranchGitAdapter=class{constructor(e,t,n,o,s){this.basePath=e,this.git=t,this.conflictDetector=n,this.logger=o,this.metrics=s,this.mode="single-agent",this.currentRequestId=null,this.currentBranch="main",this.branchManager=(0,r.createSharedBranchManager)(t,o,s)}async setupWorkspace(e){const t=Date.now()
|
|
4919
|
-
try{const r=n.WorkspaceValidation.validateRequestId(e)
|
|
4920
|
-
if(!r.isValid){const t="Invalid request ID: "+r.errors.join(", ")
|
|
4921
|
-
throw n.WorkspaceLogging.logOperation(this.logger,"error",t,e,"single-agent","setupWorkspace"),Error(t)}const o=r.sanitized,s=this.branchManager.generateRequestBranchName(o),i=await this.branchManager.getBaseBranch()
|
|
4922
|
-
n.WorkspaceLogging.logOperation(this.logger,"info","Setting up single-agent workspace",e,"single-agent","setupWorkspace",{branchName:s,mainBranch:i,currentBranch:this.currentBranch})
|
|
4923
|
-
const a=await this.git.branch(),c=a.all.includes(s)||a.all.includes("remotes/origin/"+s)
|
|
4924
|
-
if(!c)throw Error(`Branch ${s} does not exist. Use initializeRequest() first.`)
|
|
4925
|
-
n.WorkspaceLogging.logOperation(this.logger,"info","Branch exists, switching to it",e,"single-agent","setupWorkspace",{branchName:s,branchExists:c,currentBranch:this.currentBranch})
|
|
4926
|
-
const l=await this.branchManager.switchToBranch(s,o)
|
|
4927
|
-
if(!l.success){n.WorkspaceLogging.logOperation(this.logger,"warn","Branch switch failed, trying direct checkout",e,"single-agent","setupWorkspace",{branchName:s,error:l.error,attempting:"direct-checkout"})
|
|
4928
|
-
try{await this.git.checkout(s),n.WorkspaceLogging.logOperation(this.logger,"info","Direct checkout succeeded",e,"single-agent","setupWorkspace",{branchName:s})}catch(e){throw Error(`Failed to switch to branch ${s}: ${l.error}. Direct checkout also failed: ${e}`)}}this.currentBranch=s,this.currentRequestId=o
|
|
4929
|
-
const u=Date.now()-t
|
|
4930
|
-
return this.metrics?.recordValue("branch_adapter_setup_duration",u),n.WorkspaceLogging.logOperation(this.logger,"info","Successfully set up single-agent workspace",e,"single-agent","setupWorkspace",{branchName:s,mainBranch:i,duration:u}),{mode:"single-agent",requestId:o,branchName:s,workingDirectory:this.basePath,isWorktree:!1,branchInfo:{mainBranch:i,currentBranch:s}}}catch(r){const o=Date.now()-t
|
|
4931
|
-
throw this.metrics?.recordValue("branch_adapter_setup_duration",o),n.WorkspaceLogging.logOperation(this.logger,"error","Failed to set up single-agent workspace",e,"single-agent","setupWorkspace",{error:(0,s.getErrorMessage)(r),duration:o}),n.ConflictResolutionUtils.handleBranchCreationError(r instanceof Error?r:Error(r+""),e,"setup workspace","single-agent")}}async detectConflicts(e,t){n.WorkspaceLogging.logOperation(this.logger,"info","Detecting conflicts in single-agent mode",e.requestId,"single-agent","detectConflicts",{sourceBranch:t.sourceBranch,targetBranch:t.targetBranch,workingDirectory:e.workingDirectory})
|
|
4932
|
-
const r=await this.conflictDetector.detectConflicts({mode:"single-agent",logger:this.logger,requestId:t.requestId,sourceBranch:t.sourceBranch,targetBranch:t.targetBranch})
|
|
4933
|
-
return n.WorkspaceLogging.logOperation(this.logger,"info","Conflict detection completed",e.requestId,"single-agent","detectConflicts",{hasConflicts:r.hasConflicts,conflictedFiles:r.conflictedFiles.length,detectionMethod:r.detectionMethod}),r}async stageAndCommitChanges(e){const t=Date.now()
|
|
4934
|
-
n.WorkspaceLogging.logOperation(this.logger,"info","Staging and committing changes in single-agent mode",e.requestId,"single-agent","stageAndCommitChanges",{branchName:e.branchName,workingDirectory:e.workingDirectory})
|
|
4935
|
-
try{const r=await this.git.status()
|
|
4936
|
-
if(r.modified.length>0||r.not_added.length>0){n.WorkspaceLogging.logOperation(this.logger,"info","Found unstaged changes, staging resolved files",e.requestId,"single-agent","stageAndCommitChanges",{modifiedFiles:r.modified.length,untrackedFiles:r.not_added.length}),r.modified.length>0&&await this.git.add(r.modified),r.not_added.length>0&&await this.git.add(r.not_added),await this.git.commit("Resolve conflicts for request completion",{"--allow-empty":null})
|
|
4937
|
-
const o=Date.now()-t
|
|
4938
|
-
this.metrics?.recordValue("branch_stage_commit_duration",o),n.WorkspaceLogging.logOperation(this.logger,"info","Successfully staged and committed resolved files",e.requestId,"single-agent","stageAndCommitChanges",{stagedFiles:r.modified.length+r.not_added.length,duration:o})}else{const r=Date.now()-t
|
|
4939
|
-
this.metrics?.recordValue("branch_stage_commit_duration",r),n.WorkspaceLogging.logOperation(this.logger,"info","No unstaged changes found, proceeding with existing commit",e.requestId,"single-agent","stageAndCommitChanges",{duration:r})}}catch(r){const o=Date.now()-t
|
|
4940
|
-
this.metrics?.recordValue("branch_stage_commit_duration",o),n.WorkspaceLogging.logOperation(this.logger,"warn","Failed to stage resolved files, proceeding anyway",e.requestId,"single-agent","stageAndCommitChanges",{error:r instanceof Error?r.message:r+"",duration:o})}return await this.git.revparse(["HEAD"])}async executeMerge(e,t){const r=Date.now()
|
|
4941
|
-
n.WorkspaceLogging.logOperation(this.logger,"info","Executing merge in single-agent mode",e.requestId,"single-agent","executeMerge",{strategy:t.strategy,gitStrategy:t.gitStrategy,branchName:e.branchName})
|
|
4942
|
-
const s=e.branchInfo?.mainBranch||"main"
|
|
4943
|
-
try{this.logger.debug("Checking for uncommitted changes before branch switch",{mainBranch:s}),n.WorkspaceLogging.logOperation(this.logger,"info","Checking for uncommitted changes before branch switch",e.requestId,"single-agent","executeMerge",{currentBranch:e.branchName,targetBranch:s})
|
|
4944
|
-
try{const t=await(0,o.checkUncommittedChanges)(this.git,this.logger,this.metrics||{})
|
|
4945
|
-
if(this.logger.debug("Uncommitted changes check result",{hasChanges:t.hasChanges,totalFiles:t.totalFiles,staged:t.stagedFiles.length,unstaged:t.unstagedFiles.length,untracked:t.untrackedFiles.length}),t.hasChanges){this.logger.debug("Found uncommitted changes, committing before branch switch"),n.WorkspaceLogging.logOperation(this.logger,"warn","Found uncommitted changes, committing as user changes before branch switch",e.requestId,"single-agent","executeMerge",{staged:t.stagedFiles.length,unstaged:t.unstagedFiles.length,untracked:t.untrackedFiles.length,total:t.totalFiles,summary:t.summary})
|
|
4946
|
-
const r=await(0,o.commitUserChanges)(this.git,e.requestId,t,this.logger,this.metrics||{})
|
|
4947
|
-
this.logger.debug("Successfully committed user changes",{commitHash:r.commitHash.substring(0,8),filesCommitted:r.filesCommitted}),n.WorkspaceLogging.logOperation(this.logger,"info","Successfully committed user changes before branch switch",e.requestId,"single-agent","executeMerge",{commitHash:r.commitHash.substring(0,8),filesCommitted:r.filesCommitted,commitMessage:r.message.split("\n")[0]})}else this.logger.debug("No uncommitted changes detected, safe to switch branches"),n.WorkspaceLogging.logOperation(this.logger,"info","No uncommitted changes detected, proceeding with branch switch",e.requestId,"single-agent","executeMerge",{currentBranch:e.branchName,targetBranch:s})}catch(t){this.logger.debug("Failed to check/commit uncommitted changes",{error:t instanceof Error?t.message:t+""}),n.WorkspaceLogging.logOperation(this.logger,"warn","Failed to check/commit uncommitted changes, proceeding with branch switch anyway",e.requestId,"single-agent","executeMerge",{error:t instanceof Error?t.message:t+"",fallback:"continuing-with-branch-switch"})}this.logger.debug("Switching to main branch",{mainBranch:s})
|
|
4948
|
-
const i=await this.branchManager.switchToBranch(s,e.requestId)
|
|
4949
|
-
if(!i.success)throw Error("Failed to switch to main branch: "+i.error)
|
|
4950
|
-
this.logger.debug("Successfully switched to main branch",{mainBranch:s}),n.WorkspaceLogging.logOperation(this.logger,"info","Switched to main branch for merge",e.requestId,"single-agent","executeMerge",{mainBranch:s})
|
|
4951
|
-
const a=await this.git.revparse([s]),c=await this.git.revparse([e.branchName])
|
|
4952
|
-
a.trim()===c.trim()?(n.WorkspaceLogging.logOperation(this.logger,"info","Request branch has not diverged from main, creating empty commit to enable merge",e.requestId,"single-agent","executeMerge",{mainCommit:a.substring(0,8),requestCommit:c.substring(0,8),reason:"no-file-modifications"}),await this.git.checkout(e.branchName),await this.git.commit(`Empty commit for request ${e.requestId} (no file modifications)`,void 0,{"--allow-empty":null}),await this.git.checkout(s),n.WorkspaceLogging.logOperation(this.logger,"info","Created empty commit on request branch, proceeding with merge",e.requestId,"single-agent","executeMerge",{emptyCommitCreated:!0})):n.WorkspaceLogging.logOperation(this.logger,"info","Request branch has diverged from main, proceeding with normal merge",e.requestId,"single-agent","executeMerge",{mainCommit:a.substring(0,8),requestCommit:c.substring(0,8)}),"direct"===t.strategy&&"theirs"===t.gitStrategy?await this.git.merge([e.branchName,"-m",t.mergeMessage,"--no-ff","-X","theirs"]):await this.git.merge([e.branchName,"-m",t.mergeMessage,"--no-ff"])
|
|
4953
|
-
const l=Date.now()-r
|
|
4954
|
-
this.metrics?.recordValue("branch_merge_duration",l),n.WorkspaceLogging.logOperation(this.logger,"info","Merge executed successfully",e.requestId,"single-agent","executeMerge",{strategy:t.strategy,gitStrategy:t.gitStrategy||"default",duration:l})}catch(o){const s=Date.now()-r
|
|
4955
|
-
throw this.metrics?.recordValue("branch_merge_duration",s),n.WorkspaceLogging.logOperation(this.logger,"error","Merge failed in single-agent mode",e.requestId,"single-agent","executeMerge",{error:o instanceof Error?o.message:o+"",strategy:t.strategy,duration:s}),o}return{mergeCommitHash:await this.git.revparse(["HEAD"]),mergedFiles:[],strategy:t.strategy,wasAutoMerged:"auto-merge"===t.strategy}}async cleanup(e){const t=Date.now()
|
|
4956
|
-
n.WorkspaceLogging.logOperation(this.logger,"info","Cleaning up single-agent workspace",e.requestId,"single-agent","cleanup",{branchName:e.branchName,action:"preserve-branch"})
|
|
4957
|
-
const r=Date.now()-t
|
|
4958
|
-
return this.metrics?.recordValue("branch_cleanup_duration",r),n.WorkspaceLogging.logOperation(this.logger,"info","Branch preserved after completion",e.requestId,"single-agent","cleanup",{branchName:e.branchName,duration:r}),{success:!0,branchDeleted:!1,message:`Branch ${e.branchName} preserved for history`}}async ensureBranchExists(e,t){const r=Date.now()
|
|
4959
|
-
try{n.WorkspaceLogging.logOperation(this.logger,"info","Ensuring branch exists for request",e,"single-agent","ensureBranchExists",{requestTitle:t})
|
|
4960
|
-
const o=n.ConflictResolutionUtils.createStandardBranchOptions(e,t),s=await this.branchManager.createBranchWithRetry(o),i=Date.now()-r
|
|
4961
|
-
return this.metrics?.recordValue("branch_ensure_duration",i),s.success||s.existed?(n.WorkspaceLogging.logOperation(this.logger,"info","Successfully ensured branch exists",e,"single-agent","ensureBranchExists",{branchName:s.branchName,baseBranch:s.baseBranch,existed:s.existed,duration:i}),{success:!0,branchName:s.branchName,baseBranch:s.baseBranch,existed:s.existed,message:s.message}):(n.WorkspaceLogging.logOperation(this.logger,"error","Failed to ensure branch exists",e,"single-agent","ensureBranchExists",{error:s.error,duration:i}),{success:!1,branchName:s.branchName,baseBranch:s.baseBranch,existed:!1,message:s.error})}catch(o){const i=Date.now()-r
|
|
4962
|
-
this.metrics?.recordValue("branch_ensure_duration",i)
|
|
4963
|
-
const a=(0,s.getErrorMessage)(o)
|
|
4964
|
-
return n.WorkspaceLogging.logOperation(this.logger,"error","Exception during branch creation",e,"single-agent","ensureBranchExists",{error:a,duration:i}),{success:!1,branchName:this.branchManager.generateRequestBranchName(e,t),baseBranch:"unknown",existed:!1,message:a}}}updateState(e,t){t&&this.currentRequestId===e.requestId&&(this.currentRequestId=null,this.currentBranch=e.branchInfo?.mainBranch||"main"),n.WorkspaceLogging.logOperation(this.logger,"info","Updated single-agent state",e.requestId,"single-agent","updateState",{completed:t,currentRequestId:this.currentRequestId,currentBranch:this.currentBranch})}getMainGit(){return this.git}}},9030(e,exports,t){"use strict"
|
|
4771
|
+
let s=null,i=!1,a=null},9030(e,exports,t){"use strict"
|
|
4965
4772
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.def=void 0
|
|
4966
4773
|
const r=t(6183),n=t(4079)
|
|
4967
4774
|
exports.def={name:"write_file",description:"Write content to files or documents. Supports both filesystem files (using 'path') and tracked documents (using 'documentId'). For files: requires a taskId and comment, creates/overwrites files, and commits to git. For documents: writes to cached document and syncs back to tracking system. Set append:true to add content to existing content. Handles both text and JSON content.",schema:r.WriteFileSchema,annotations:{title:"Write File/Document",readOnlyHint:!1,destructiveHint:!0,idempotentHint:!1},createsRecords:!0,handler(e,t){return(0,n.handleWriteFile)(e,t.context,t.apiClient.getFileClient(),t.apiClient.getTaskClient(),t.apiClient.getToolRecordClient(),t.apiClient.getRequestClient(),t.logger,t.metrics,t.mcpServer)}}},9060(e,exports,t){"use strict"
|
|
4968
4775
|
var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}}
|
|
4969
4776
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.ConfigManager=void 0,exports.createConfigManager=function(e){return new u(e)}
|
|
4970
|
-
const n=r(t(1943)),o=r(t(6928)),s=r(t(857)),i=t(4139),a=t(8824),c={
|
|
4777
|
+
const n=r(t(1943)),o=r(t(6928)),s=r(t(857)),i=t(4139),a=t(8824),c={lockOverride:{enabled:!0,passwordValidityMinutes:5}},l={remoteServerUrl:"https://api.alchemylabcode.com",nodePath:"node"}
|
|
4971
4778
|
class u{constructor(e){this.logger=e.child({component:"config-manager"}),this.installationConfigDir=this.getInstallationConfigDir()}getInstallationConfigDir(){const e=__dirname||process.cwd(),t=s.default.homedir()
|
|
4972
4779
|
return e.includes("node_modules")?o.default.join(t,".alchemy_lab","config"):o.default.join(t,".alchemy_lab","config-dev")}async ensureDirectory(e){try{await n.default.access(e)}catch(t){await n.default.mkdir(e,{recursive:!0}),this.logger.debug("Created directory",{dirPath:e})}}async readConfig(e,t){try{const r=await n.default.readFile(e,"utf8"),o=JSON.parse(r)
|
|
4973
4780
|
return{...t,...o}}catch(r){return"ENOENT"===r.code||this.logger.warn("Error reading config file, using defaults",{filePath:e,error:(0,a.getErrorMessage)(r)}),t}}async writeConfig(e,t){await this.ensureDirectory(o.default.dirname(e)),await n.default.writeFile(e,JSON.stringify(t,null,2),"utf8"),this.logger.debug("Wrote config file",{filePath:e})}async getProjectConfig(e){const t=o.default.join(e,i.ALCHEMY_DIR_NAME,"config.json")
|
|
@@ -4977,7 +4784,7 @@ try{const e=await n.default.readFile(t,"utf8"),r=JSON.parse(e)
|
|
|
4977
4784
|
return{id:r.id,name:r.name,createdAt:r.createdAt,status:r.status}}catch(e){return"ENOENT"===e.code||this.logger.warn("Error reading project metadata",{projectJsonPath:t,error:(0,a.getErrorMessage)(e)}),null}}async getInstallationConfig(){const e=o.default.join(this.installationConfigDir,"config.json")
|
|
4978
4785
|
return this.readConfig(e,l)}async updateInstallationConfig(e){const t=o.default.join(this.installationConfigDir,"config.json"),r={...await this.getInstallationConfig(),...e}
|
|
4979
4786
|
await this.writeConfig(t,r),this.logger.info("Updated installation config",{updates:e})}async getEffectiveConfig(e){const[t,r,n]=await Promise.all([this.getProjectConfig(e),this.getProjectMetadata(e),this.getInstallationConfig()])
|
|
4980
|
-
return{remoteServerUrl:n.remoteServerUrl||l.remoteServerUrl,nodePath:n.nodePath||l.nodePath,projectId:r?.id,projectName:r?.name,
|
|
4787
|
+
return{remoteServerUrl:n.remoteServerUrl||l.remoteServerUrl,nodePath:n.nodePath||l.nodePath,projectId:r?.id,projectName:r?.name,lockOverride:{enabled:t.lockOverride?.enabled??c.lockOverride.enabled,passwordValidityMinutes:t.lockOverride?.passwordValidityMinutes??c.lockOverride.passwordValidityMinutes}}}getInstallationConfigPath(){return this.installationConfigDir}}exports.ConfigManager=u},9067(e,exports,t){"use strict"
|
|
4981
4788
|
var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}}
|
|
4982
4789
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.ExternalAuthFlow=exports.PollingStatus=void 0
|
|
4983
4790
|
const n=r(t(6982)),o=t(8824)
|
|
@@ -5062,7 +4869,7 @@ const d=l.getSessionMessageClient()
|
|
|
5062
4869
|
if(!d)throw new c.ValidationError("Session message client not available")
|
|
5063
4870
|
if("question"===u)return await async function(e,t,i,a,l){const{toSessionId:u,questionType:d,questionContent:h,priority:g,expiresInHours:p}=e
|
|
5064
4871
|
if(!d||!h?.question)throw new c.ValidationError("Question requires questionType and questionContent.question")
|
|
5065
|
-
const f=
|
|
4872
|
+
const f=o(0,0,"session_message_operations"),m=await async function(e,t,r,o){if("parent"===e){const e=await n(t,r,o)
|
|
5066
4873
|
if(!e)throw new c.ValidationError("Could not find parent session. Make sure this session was spawned as a subagent.")
|
|
5067
4874
|
return o.info('Resolved toSessionId "parent" to actual ID',{parentId:e}),e}return e}(u,f,a,i)
|
|
5068
4875
|
if(!("alternatives"!==d||h.options&&Array.isArray(h.options)))throw new c.ValidationError("Alternatives questions require options array")
|
|
@@ -5074,7 +4881,7 @@ if(t.context&&r.push("**Context:** "+t.context),"alternatives"===t.questionType&
|
|
|
5074
4881
|
for(const e of t.options)r.push(` - [${e.id}] ${e.label}${e.description?" - "+e.description:""}`)}return r.push(""),r.push(`Use \`session_message_operations\` with \`reply\` operation and message code \`${e.messageCode}\` to respond.`),r.join("\n")}(y),t,i)?"\n\n\u{1f4ec} The target session has been notified.":"\n\n\u26a0\ufe0f Could not notify the target session (may be offline)."),{content:[{type:"text",text:`\u2705 Question created!${w}\n\n**Message Code: ${y.messageCode}**\n\nUse this code to check for answers or share with other sessions.\n\n${s(y)}`}]}}(e,t,a,l,d)
|
|
5075
4882
|
if("report"===u)return await async function(e,t,s,a,l){const{status:u,summary:d,details:h,finish:p}=e
|
|
5076
4883
|
if(!u||!d)throw new c.ValidationError("Report requires status and summary")
|
|
5077
|
-
const f=
|
|
4884
|
+
const f=o(0,0,"session_message_operations"),m=await(async()=>{if(e.toSessionId&&"parent"!==e.toSessionId)return s.info("Using explicit toSessionId for report",{parentSessionId:e.toSessionId}),e.toSessionId
|
|
5078
4885
|
const t=await n(f,a,s)
|
|
5079
4886
|
if(!t)throw new c.ValidationError("Could not find parent session. This tool should only be used by subagent sessions.")
|
|
5080
4887
|
return s.info("Auto-resolved parent session",{parentSessionId:t}),t})()
|
|
@@ -5134,26 +4941,14 @@ if(t>0){const r=e.slice(0,t).trim()
|
|
|
5134
4941
|
return exports.SCIENTIST_NAMES.find((e=>e.toLowerCase()===r.toLowerCase()))??null}return exports.SCIENTIST_NAMES.find((t=>t.toLowerCase()===e.trim().toLowerCase()))??null}Object.defineProperty(exports,"__esModule",{value:!0}),exports.SCIENTIST_NAMES=void 0,exports.pickSpecialistName=function(e){const r=new Set(e.map(t).filter((e=>null!==e))),n=exports.SCIENTIST_NAMES.filter((e=>!r.has(e)))
|
|
5135
4942
|
return 0===n.length?`${exports.SCIENTIST_NAMES[Math.floor(Math.random()*exports.SCIENTIST_NAMES.length)]}-${e.length+1}`:n[Math.floor(Math.random()*n.length)]},exports.SCIENTIST_NAMES=["Archimedes","Avicenna","Boyle","Brahe","Copernicus","Curie","Darwin","Euclid","Euler","Faraday","Fermi","Fibonacci","Galileo","Gauss","Hooke","Hypatia","Kepler","Lavoisier","Leibniz","Lovelace","Maxwell","Mendeleev","Newton","Nobel","Pascal","Pasteur","Planck","Ptolemy","Tesla","Turing"]},9150(module){"use strict"
|
|
5136
4943
|
module.exports=require("@modelcontextprotocol/sdk/types.js")},9161(e,exports,t){"use strict"
|
|
5137
|
-
|
|
5138
|
-
const
|
|
5139
|
-
class
|
|
4944
|
+
Object.defineProperty(exports,"__esModule",{value:!0}),exports.ConflictDetector=void 0,exports.createConflictDetector=function(e,t){return new i(e,t)}
|
|
4945
|
+
const r=t(8824),n=t(3444),o=t(8712),s=n.defaultLogger.child({component:"conflict-detector"})
|
|
4946
|
+
class i{constructor(e,t){this.git=e,this.logger=t}async detectConflicts(e){const t=e.logger.child({component:"conflict-detector",mode:e.mode,requestId:e.requestId,sourceBranch:e.sourceBranch,targetBranch:e.targetBranch})
|
|
5140
4947
|
t.info("Starting conflict detection",{mode:e.mode,detectionStrategy:"merge-tree-analysis"})
|
|
5141
|
-
try{return
|
|
5142
|
-
try{const r=await this.git.revparse([e.sourceBranch]),n=await this.git.revparse([e.targetBranch])
|
|
5143
|
-
let o,i
|
|
5144
|
-
t.debug("Retrieved commits for merge-tree analysis",{sourceCommit:r.substring(0,8),targetCommit:n.substring(0,8),sourceBranch:e.sourceBranch,targetBranch:e.targetBranch})
|
|
5145
|
-
try{o=await this.git.raw(["merge-base",r,n])}catch(o){return t.warn("Could not find merge-base, commits may be unrelated",{sourceCommit:r.substring(0,8),targetCommit:n.substring(0,8),error:o}),{hasConflicts:!0,conflictedFiles:[{path:"<multiple files>",conflictType:"content",description:"Branches have diverged significantly (no merge-base found)"}],summary:"Branches have diverged significantly",resolutionInstructions:this.generateSingleAgentInstructions([{path:"<multiple files>",conflictType:"content",description:"Significant divergence"}],e.requestId,e.sourceBranch,e.targetBranch),detectionMethod:"merge-tree-analysis",rawOutput:"merge-base failed: "+o}}t.debug("Commits for merge-tree analysis",{sourceCommit:r.substring(0,8),targetCommit:n.substring(0,8),mergeBase:o.trim().substring(0,8)})
|
|
5146
|
-
let a=0
|
|
5147
|
-
try{i=await this.git.raw(["merge-tree",o.trim(),n.trim(),r.trim()]),a=0}catch(e){i=e.message||"",a=e.exitCode||1,t.debug("merge-tree failed with error",{exitCode:a,error:e.message})}t.debug("Merge-tree analysis completed",{outputLength:i.length,hasOutput:!!i.trim(),exitCode:a})
|
|
5148
|
-
let c=!1,l="",u=null
|
|
5149
|
-
if(0!==a?(c=!0,l="merge-tree-exit-code"):i&&i.trim()?(u=(0,s.parseConflictOutputWithContext)(i,e.requestId,e.sourceBranch,e.targetBranch),u.hasConflictMarkers?(c=!0,l="conflict-parser-detected-markers",t.warn("Git exit code 0 but conflict parser found conflict markers - treating as conflict")):(c=!1,l="clean-merge-with-changes",t.info("Git exit code 0 and conflict parser found no markers - treating as clean merge",{hasOutput:!0,outputLength:i.length}))):(c=!1,l="clean-merge-no-changes"),t.info("UNIFIED conflict detection result (same logic as multi-agent)",{hasConflicts:c,exitCode:a,hasOutput:!!i.trim(),outputLength:i?i.length:0,conflictReason:l,method:"git-merge-tree-unified",trustedGitExitCode:0===a}),!c)return{hasConflicts:!1,conflictedFiles:[],summary:"No conflicts detected (merge-tree clean)",resolutionInstructions:"",detectionMethod:"merge-tree-analysis",rawOutput:i}
|
|
5150
|
-
!u&&i&&i.trim()&&(u=(0,s.parseConflictOutputWithContext)(i,e.requestId,e.sourceBranch,e.targetBranch))
|
|
5151
|
-
let d=[]
|
|
5152
|
-
if(u&&u.filesParsed&&u.filesParsed.length>0)d=u.filesParsed.map((e=>({path:e,conflictType:"content",description:"Merge conflict detected"}))),t.debug("Successfully extracted conflict files from parsed content",{conflictedFilesCount:d.length,files:d.map((e=>e.path))})
|
|
5153
|
-
else try{d=this.parseMergeTreeOutput(i,t),t.debug("Used fallback merge-tree parsing",{conflictedFilesCount:d.length})}catch(e){t.warn("Both conflict parsing methods failed",{parseError:e instanceof Error?e.message:e+""}),d=[{path:"<parsing failed>",conflictType:"content",description:"Git detected conflicts but parsing failed - manual inspection required"}]}return 0===d.length&&(t.warn("Git detected conflicts but no files could be determined - using fallback"),d=[{path:"<unknown files>",conflictType:"content",description:"Git detected conflicts but could not determine specific files"}]),{hasConflicts:!0,conflictedFiles:d,summary:d.length>0&&"<parsing failed>"!==d[0].path&&"<unknown files>"!==d[0].path?d.length+" file(s) have merge conflicts (detected by Git)":"Merge conflicts detected by Git (parsing details failed)",resolutionInstructions:this.generateSingleAgentInstructions(d,e.requestId,e.sourceBranch,e.targetBranch),detectionMethod:"merge-tree-analysis",rawOutput:i,rawConflictContent:u?u.cleanContent:void 0}}catch(e){throw t.error("Unified single-agent conflict detection failed",{error:e}),e}}async detectMultiAgentConflicts(e,r){if(r.info("Using pure merge-tree analysis for multi-agent conflict detection",{worktreePath:e.worktreePath}),!e.worktreePath)throw Error("worktreePath is required for multi-agent conflict detection")
|
|
4948
|
+
try{return await this.detectMultiAgentConflicts(e,t)}catch(e){return t.error("Conflict detection failed",{error:e}),{hasConflicts:!1,conflictedFiles:[],summary:"Conflict detection failed - proceeding with caution",resolutionInstructions:"Conflict detection failed: "+(0,r.getErrorMessage)(e),detectionMethod:"merge-tree-analysis",rawOutput:(0,r.getErrorMessage)(e)}}}async detectMultiAgentConflicts(e,r){if(r.info("Using pure merge-tree analysis for multi-agent conflict detection",{worktreePath:e.worktreePath}),!e.worktreePath)throw Error("worktreePath is required for multi-agent conflict detection")
|
|
5154
4949
|
try{r.debug("Getting worktree commit for analysis")
|
|
5155
|
-
const n=t(3807)(e.worktreePath),
|
|
5156
|
-
if(r.info("WORKTREE DEBUG: Current branch status",{requestId:e.requestId,currentBranch:
|
|
4950
|
+
const n=t(3807)(e.worktreePath),s=await n.branch()
|
|
4951
|
+
if(r.info("WORKTREE DEBUG: Current branch status",{requestId:e.requestId,currentBranch:s.current,expectedBranch:e.sourceBranch,allBranches:s.all,isDetached:s.detached}),s.current!==e.sourceBranch&&s.current!==e.sourceBranch.replace("refs/heads/","")){r.warn("WORKTREE BRANCH MISMATCH",{requestId:e.requestId,currentBranch:s.current,expectedBranch:e.sourceBranch,worktreePath:e.worktreePath})
|
|
5157
4952
|
try{await n.checkout(e.sourceBranch.replace("refs/heads/","")),r.info("Successfully switched to correct branch",{requestId:e.requestId,branch:e.sourceBranch})}catch(t){r.error("Failed to checkout correct branch",{requestId:e.requestId,expectedBranch:e.sourceBranch,error:t})}}const i=await n.revparse(["HEAD"])
|
|
5158
4953
|
let a=!1
|
|
5159
4954
|
try{await this.git.raw(["merge-base","--is-ancestor",i,"main"]),a=!0}catch{a=!1}r.info("WORKTREE DEBUG: HEAD commit analysis",{requestId:e.requestId,commit:i.substring(0,8),fullCommit:i,sourceBranch:e.sourceBranch,isCommitInMain:a,worktreePath:e.worktreePath}),a&&r.warn("POTENTIAL BUG: Worktree HEAD points to commit already in main",{requestId:e.requestId,worktreeCommit:i.substring(0,8),sourceBranch:e.sourceBranch,warning:"This may cause false negative conflict detection"})
|
|
@@ -5163,8 +4958,8 @@ try{l=await this.git.raw(["merge-base",i,c])}catch(t){return r.warn("Could not f
|
|
|
5163
4958
|
let d=0
|
|
5164
4959
|
try{u=await this.git.raw(["merge-tree",l.trim(),c.trim(),i.trim()]),d=0}catch(e){u=e.message||"",d=e.exitCode||1,r.debug("merge-tree failed with error",{exitCode:d,error:e.message})}r.debug("Merge-tree analysis completed",{outputLength:u.length,hasOutput:!!u.trim(),exitCode:d})
|
|
5165
4960
|
let h=!1,g="",p=null
|
|
5166
|
-
if(0!==d?(h=!0,g="merge-tree-exit-code"):u&&u.trim()?(p=(0,
|
|
5167
|
-
!p&&u&&u.trim()&&(p=(0,
|
|
4961
|
+
if(0!==d?(h=!0,g="merge-tree-exit-code"):u&&u.trim()?(p=(0,o.parseConflictOutputWithContext)(u,e.requestId,e.sourceBranch,e.targetBranch),p.hasConflictMarkers?(h=!0,g="conflict-parser-detected-markers",r.warn("Git exit code 0 but conflict parser found conflict markers - treating as conflict")):(h=!1,g="clean-merge-with-changes",r.info("Git exit code 0 and conflict parser found no markers - treating as clean merge",{hasOutput:!0,outputLength:u.length}))):(h=!1,g="clean-merge-no-changes"),r.info("FINAL conflict detection result (trusting Git exit codes)",{hasConflicts:h,exitCode:d,hasOutput:!!u.trim(),outputLength:u?u.length:0,conflictReason:g,method:"git-exit-code-primary",trustedGitExitCode:0===d}),!h)return{hasConflicts:!1,conflictedFiles:[],summary:"No conflicts detected (merge-tree clean)",resolutionInstructions:"",detectionMethod:"merge-tree-analysis",rawOutput:u}
|
|
4962
|
+
!p&&u&&u.trim()&&(p=(0,o.parseConflictOutputWithContext)(u,e.requestId,e.sourceBranch,e.targetBranch))
|
|
5168
4963
|
let f=[]
|
|
5169
4964
|
if(p&&p.filesParsed&&p.filesParsed.length>0)f=p.filesParsed.map((e=>({path:e,conflictType:"content",description:"Merge conflict detected"}))),r.debug("Successfully extracted conflict files from parsed content",{conflictedFilesCount:f.length,files:f.map((e=>e.path))})
|
|
5170
4965
|
else try{f=this.parseMergeTreeOutput(u,r),r.debug("Used fallback merge-tree parsing",{conflictedFilesCount:f.length})}catch(e){r.warn("Both conflict parsing methods failed",{parseError:e instanceof Error?e.message:e+""}),f=[{path:"<parsing failed>",conflictType:"content",description:"Git detected conflicts but parsing failed - manual inspection required"}]}return 0===f.length&&(r.warn("Git detected conflicts but no files could be determined - using fallback"),f=[{path:"<unknown files>",conflictType:"content",description:"Git detected conflicts but could not determine specific files"}]),{hasConflicts:!0,conflictedFiles:f,summary:f.length>0&&"<parsing failed>"!==f[0].path&&"<unknown files>"!==f[0].path?f.length+" file(s) have merge conflicts (detected by Git)":"Merge conflicts detected by Git (parsing details failed)",resolutionInstructions:this.generateMultiAgentInstructions(f,e.requestId,e.worktreePath,e.targetBranch),detectionMethod:"merge-tree-analysis",rawOutput:u,rawConflictContent:p?p.cleanContent:void 0}}catch(e){throw r.error("Pure multi-agent conflict detection failed",{error:e}),e}}parseMergeTreeOutput(e,t){const r=[]
|
|
@@ -5181,27 +4976,18 @@ for(let i=e+1;i<Math.min(e+10,n.length);i++){const e=n[i].trim().match(/^(?:our|
|
|
|
5181
4976
|
if(e){const n=e[1].trim(),i=n.includes(" -> ")?n.split(" -> ")[1]||n.split(" -> ")[0]:n
|
|
5182
4977
|
i&&!s.has(i)&&(s.add(i),r.push({path:i,conflictType:o,description:t+" conflict"}))}}}const o=t.match(/CONFLICT\\s*\\([^)]+\\):\\s*.*?(?:in|->)\\s+(.+?)(?:\\s*->\\s*(.+?))?$/i)
|
|
5183
4978
|
if(o){const e=o[1].trim()
|
|
5184
|
-
e&&"Merge conflict"!==e&&!s.has(e)&&(s.add(e),r.push({path:e,conflictType:"content",description:"CONFLICT message detected"}))}}return t.debug("Parsed conflicted files from merge-tree",{filesCount:r.length,files:r.map((e=>e.path))}),r}
|
|
5185
|
-
|
|
5186
|
-
const t=["changed in both","added in both","deleted by us","deleted by them","renamed in both","CONFLICT(","conflict:","failed to merge"]
|
|
5187
|
-
for(const r of t)if(e.toLowerCase().includes(r.toLowerCase()))return this.logger.debug("Found conflict keyword",{keyword:r}),!0
|
|
5188
|
-
this.logger.debug("No conflict keywords found")
|
|
5189
|
-
const r=e.split("\n")
|
|
5190
|
-
let n=!1
|
|
5191
|
-
for(const e of r){const t=e.trim()
|
|
5192
|
-
if(/^[UA]{2}\s+/.test(t)||/^DD\s+/.test(t)){this.logger.debug("Found git status conflict indicator",{line:t}),n=!0
|
|
5193
|
-
break}}return!!n||(e.includes("merged\n")&&e.includes("result ")&&e.includes("our ")?(this.logger.debug("Detected clean merge format"),!1):(this.logger.debug("No conflict indicators found, assuming clean merge"),!1))}generateSingleAgentInstructions(e,t,r,n){return`MERGE CONFLICTS DETECTED - Resolution Required\n\nConflicted Files:\n${e.map((e=>`- ${e.path} (${e.conflictType} conflict)`)).join("\\n")}\n\nResolution Steps for Single-Agent Mode:\n1. Switch to your feature branch: git checkout ${r}\n2. Merge ${n} into your feature branch: git merge ${n}\n3. Resolve conflicts in each file:\n ${e.map((e=>` - Edit ${e.path} to resolve ${e.conflictType} conflict`)).join("\\n")}\n4. Stage resolved files: git add ${e.map((e=>e.path)).join(" ")}\n5. Commit the resolution: git commit -m "Resolve merge conflicts for request ${t}"\n6. Try completing the request again\n\nThe conflicts must be resolved before the request can be completed.`}generateMultiAgentInstructions(e,t,r,n){return`MERGE CONFLICTS DETECTED - Resolution Required\n\nConflicted Files:\n${e.map((e=>`- ${e.path} (${e.conflictType} conflict)`)).join("\\n")}\n\nResolution Steps for Multi-Agent Mode:\n1. Ensure you're working in the worktree: ${r}\n2. Pull latest ${n} changes: git pull origin ${n}\n3. Resolve conflicts in each file:\n ${e.map((e=>` - Edit ${e.path} to resolve ${e.conflictType} conflict`)).join("\\n")}\n4. Stage resolved files: git add ${e.map((e=>e.path)).join(" ")}\n5. Commit the resolution: git commit -m "Resolve merge conflicts for request ${t}"\n6. Try completing the request again\n\nIMPORTANT: Work only in the worktree (${r}) to avoid affecting other agents.`}hasExactConflictMarkers(e){if(!e||!e.trim())return!1
|
|
5194
|
-
i.debug("Checking for conflict markers",{textLength:e.length,firstChars:e.substring(0,100),containsStart:e.includes("<<<<<<<"),containsMiddle:e.includes("======="),containsEnd:e.includes(">>>>>>>")})
|
|
4979
|
+
e&&"Merge conflict"!==e&&!s.has(e)&&(s.add(e),r.push({path:e,conflictType:"content",description:"CONFLICT message detected"}))}}return t.debug("Parsed conflicted files from merge-tree",{filesCount:r.length,files:r.map((e=>e.path))}),r}generateMultiAgentInstructions(e,t,r,n){return`MERGE CONFLICTS DETECTED - Resolution Required\n\nConflicted Files:\n${e.map((e=>`- ${e.path} (${e.conflictType} conflict)`)).join("\\n")}\n\nResolution Steps for Multi-Agent Mode:\n1. Ensure you're working in the worktree: ${r}\n2. Pull latest ${n} changes: git pull origin ${n}\n3. Resolve conflicts in each file:\n ${e.map((e=>` - Edit ${e.path} to resolve ${e.conflictType} conflict`)).join("\\n")}\n4. Stage resolved files: git add ${e.map((e=>e.path)).join(" ")}\n5. Commit the resolution: git commit -m "Resolve merge conflicts for request ${t}"\n6. Try completing the request again\n\nIMPORTANT: Work only in the worktree (${r}) to avoid affecting other agents.`}hasExactConflictMarkers(e){if(!e||!e.trim())return!1
|
|
4980
|
+
s.debug("Checking for conflict markers",{textLength:e.length,firstChars:e.substring(0,100),containsStart:e.includes("<<<<<<<"),containsMiddle:e.includes("======="),containsEnd:e.includes(">>>>>>>")})
|
|
5195
4981
|
const t=e.split("\n")
|
|
5196
|
-
|
|
4982
|
+
s.debug("Text lines",{totalLines:t.length})
|
|
5197
4983
|
for(let e=0;e<t.length;e++){const r=t[e],n=r.trim()
|
|
5198
|
-
if(this.hasExactMarker(n,"<")||this.hasExactMarker(n,"=")||this.hasExactMarker(n,">"))return
|
|
4984
|
+
if(this.hasExactMarker(n,"<")||this.hasExactMarker(n,"=")||this.hasExactMarker(n,">"))return s.debug("Found conflict marker",{lineNumber:e+1,line:r}),!0;(r.includes("<<<<<<<")||r.includes("=======")||r.includes(">>>>>>>"))&&s.debug("Line contains marker but hasExactMarker failed",{lineNumber:e+1,line:r,trimmed:n,hasStart:this.hasExactMarker(n,"<"),hasMiddle:this.hasExactMarker(n,"="),hasEnd:this.hasExactMarker(n,">")})}return s.debug("No conflict markers detected"),!1}hasExactMarker(e,t){const r=t.repeat(7)
|
|
5199
4985
|
return!!e.startsWith(r)&&(7===e.length||e[7]!==t)}hasExplicitConflictMarkers(e){if(!e||!e.trim())return!1
|
|
5200
4986
|
if(this.logger.debug("Checking for explicit conflict markers (conservative)",{outputLength:e.length,firstLine:e.split("\n")[0]}),this.hasExactConflictMarkers(e))return this.logger.debug("Found actual Git conflict markers"),!0
|
|
5201
4987
|
if(e.includes("CONFLICT("))return this.logger.debug("Found explicit CONFLICT message from Git"),!0
|
|
5202
4988
|
const t=e.split("\n")
|
|
5203
4989
|
for(const e of t){const t=e.trim()
|
|
5204
|
-
if(/^[UA]{2}\s+/.test(t)||/^DD\s+/.test(t))return this.logger.debug("Found git status conflict indicator",{line:t}),!0}return this.logger.debug("No explicit conflict markers found - assuming clean merge"),!1}}exports.ConflictDetector=
|
|
4990
|
+
if(/^[UA]{2}\s+/.test(t)||/^DD\s+/.test(t))return this.logger.debug("Found git status conflict indicator",{line:t}),!0}return this.logger.debug("No explicit conflict markers found - assuming clean merge"),!1}}exports.ConflictDetector=i},9196(e,exports,t){"use strict"
|
|
5205
4991
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.def=void 0
|
|
5206
4992
|
const r=t(6183),n=t(8309)
|
|
5207
4993
|
exports.def={name:"create_directory",description:"Create a new directory or ensure a directory exists. Can create multiple nested directories in one operation. If the directory already exists, this operation will succeed silently. Perfect for setting up directory structures for projects or ensuring required paths exist.",schema:r.CreateDirectorySchema,annotations:{title:"Create Directory",readOnlyHint:!1,destructiveHint:!1,idempotentHint:!0},hidden:!0,handler(e,t){return(0,n.handleCreateDirectory)(e,t.context,t.apiClient.getTaskClient(),t.apiClient.getToolRecordClient(),t.apiClient.getRequestClient(),t.logger,t.metrics,t.mcpServer)}}},9230(e,exports,t){"use strict"
|
|
@@ -5256,39 +5042,39 @@ b.info("Replace in files batch operation",{taskId:_,operationCount:E.length,tota
|
|
|
5256
5042
|
const T=E.filter((e=>e.documentId)).map((e=>e.documentId))
|
|
5257
5043
|
if(T.length>0&&t.apiClient)try{await(0,m.ensureDocumentsNotLocked)(T,t.apiClient,b,a,"replace_in_files-documents")}catch(e){if(e instanceof g.ValidationError)return{content:[{type:"text",text:e.message}],isError:!0}
|
|
5258
5044
|
throw e}C=d.FileOperationPhase.TASK_VALIDATION,a.incrementCounter("replace_in_files_phase",1,{phase:C})
|
|
5259
|
-
const
|
|
5260
|
-
let
|
|
5261
|
-
const x=await d.validateTaskId(_,
|
|
5045
|
+
const R=E[0],P=R.documentId?"document:"+R.documentId:R.path
|
|
5046
|
+
let M=Date.now()
|
|
5047
|
+
const x=await d.validateTaskId(_,P,r,b,a,"replace_in_files")
|
|
5262
5048
|
Date.now()
|
|
5263
|
-
const
|
|
5049
|
+
const j=x?.requestId,O=E.some((e=>e.path))
|
|
5264
5050
|
let $=!1
|
|
5265
|
-
if(j
|
|
5266
|
-
const e=await d.validateWorkItemStates(_,
|
|
5267
|
-
Date.now(),
|
|
5268
|
-
const n=await d.autoPromoteTaskStatus(_,x.status,
|
|
5269
|
-
n.taskPromoted&&b.info("Auto-promoted task to in_progress",{taskId:_,requestId:
|
|
5270
|
-
const o=await d.ensureCorrectWorkspaceContext({taskPromoted:n.taskPromoted,requestId:
|
|
5051
|
+
if(O&&j){M=Date.now()
|
|
5052
|
+
const e=await d.validateWorkItemStates(_,P,r,s,t,b,a,"replace_in_files")
|
|
5053
|
+
Date.now(),M=Date.now()
|
|
5054
|
+
const n=await d.autoPromoteTaskStatus(_,x.status,j,e.request?.status,P,r,s,b,a,"replace_in_files")
|
|
5055
|
+
n.taskPromoted&&b.info("Auto-promoted task to in_progress",{taskId:_,requestId:j,previousStatus:x.status,newStatus:n.newTaskStatus}),Date.now(),M=Date.now()
|
|
5056
|
+
const o=await d.ensureCorrectWorkspaceContext({taskPromoted:n.taskPromoted,requestId:j,context:t,operation:"replace_in_files",logger:b,metrics:a,metricsPrefix:"replace_in_files"})
|
|
5271
5057
|
if(!o.success){if(o.isLockConflict)return{content:[{type:"text",text:"\u274c "+o.error}],isError:!0}
|
|
5272
|
-
throw Error(o.error)}Date.now(),$=!0}if(T.length>0&&
|
|
5273
|
-
throw e}
|
|
5058
|
+
throw Error(o.error)}Date.now(),$=!0}if(T.length>0&&j)try{await(0,p.validateRequestStatusForDocumentOperation)(j,s,b,a,"replace_in_files-documents")}catch(e){if(e instanceof g.ValidationError)return{content:[{type:"text",text:e.message}],isError:!0}
|
|
5059
|
+
throw e}M=Date.now()
|
|
5274
5060
|
const D=new Map
|
|
5275
|
-
if(b.info("\u{1f50d} Starting external edit detection",{hasFileOperations:
|
|
5061
|
+
if(b.info("\u{1f50d} Starting external edit detection",{hasFileOperations:O,hasGit:!!t.git,operationCount:E.length}),O&&t.git)for(const e of E)if(e.path&&!e.documentId)try{const r=d.validateAndNormalizePath(e.path,t),n=await l.default.readFile(r.fullPath,"utf8"),o=void 0!==e.fuzzy_match?e.fuzzy_match:q,s=[]
|
|
5276
5062
|
for(const t of e.replacements){const r=(0,h.findMatches)(n,t.old,o,100,e.path)
|
|
5277
5063
|
s.push(...r)}if(s.length>0){const o=(0,y.calculateReplacementRegion)(n,s,r.fullPath)
|
|
5278
5064
|
b.info("\u{1f50d} Checking for external edits",{path:r.normalizedPath,affectedLines:o.lineRanges.map((e=>`${e.start}-${e.end}`)).join(", "),matchCount:s.length})
|
|
5279
5065
|
const i=await(0,w.detectExternalEdits)(t.git,o,b)
|
|
5280
|
-
b.info("\u{1f50d} External edit detection result",{path:r.normalizedPath,hasExternalEdits:i.hasExternalEdits,conflictingLines:i.conflictingLines,hasMessage:!!i.message}),i.hasExternalEdits&&i.message?(D.set(e.path,{message:i.message,debugInfo:i.debugInfo}),b.warn("\u26a0\ufe0f External edits detected before auto-commit",{path:r.normalizedPath,conflictingLines:i.conflictingLines})):(i.debugInfo&&D.set(e.path,{message:"",debugInfo:i.debugInfo}),b.info("\u2705 No external edit conflicts detected",{path:r.normalizedPath}))}else b.info("\u2139\ufe0f No matches found for external edit detection",{path:r.normalizedPath}),D.set(e.path,{message:"",debugInfo:{detectionRan:!1,reason:"No matches found - patterns not found in file",affectedRegion:"none",uncommittedChanges:"not checked",overlapDetected:!1}})}catch(t){b.warn("Failed to check for external edits before auto-commit",{path:e.path,error:(0,k.getErrorMessage)(t)})}if(Date.now(),
|
|
5281
|
-
const e=await(0,f.commitUserChangesBeforeToolOperation)(t.git,"replace_in_files",{requestId:
|
|
5282
|
-
e.userChangesCommitted&&(b.debug("[REPLACE-IN-FILES] User changes committed",{commitHash:e.commitHash?.substring(0,8),filesCommitted:e.filesCommitted}),b.info("User changes committed before batch operation",{taskId:_,userCommitHash:e.commitHash?.substring(0,8),userFilesCommitted:e.filesCommitted}))}catch(e){b.warn("Pre-tool user changes commit failed",{taskId:_,error:e instanceof Error?e.message:e+""})}Date.now(),
|
|
5283
|
-
const{toolRecordId:A}=await d.createFileOperationRecords(_,
|
|
5284
|
-
v=A,Date.now(),
|
|
5066
|
+
b.info("\u{1f50d} External edit detection result",{path:r.normalizedPath,hasExternalEdits:i.hasExternalEdits,conflictingLines:i.conflictingLines,hasMessage:!!i.message}),i.hasExternalEdits&&i.message?(D.set(e.path,{message:i.message,debugInfo:i.debugInfo}),b.warn("\u26a0\ufe0f External edits detected before auto-commit",{path:r.normalizedPath,conflictingLines:i.conflictingLines})):(i.debugInfo&&D.set(e.path,{message:"",debugInfo:i.debugInfo}),b.info("\u2705 No external edit conflicts detected",{path:r.normalizedPath}))}else b.info("\u2139\ufe0f No matches found for external edit detection",{path:r.normalizedPath}),D.set(e.path,{message:"",debugInfo:{detectionRan:!1,reason:"No matches found - patterns not found in file",affectedRegion:"none",uncommittedChanges:"not checked",overlapDetected:!1}})}catch(t){b.warn("Failed to check for external edits before auto-commit",{path:e.path,error:(0,k.getErrorMessage)(t)})}if(Date.now(),M=Date.now(),O&&t.git)try{b.debug("[REPLACE-IN-FILES] Checking for user changes before batch operation")
|
|
5067
|
+
const e=await(0,f.commitUserChangesBeforeToolOperation)(t.git,"replace_in_files",{requestId:j,taskId:_,workspaceManager:t.workspaceManager},b,a)
|
|
5068
|
+
e.userChangesCommitted&&(b.debug("[REPLACE-IN-FILES] User changes committed",{commitHash:e.commitHash?.substring(0,8),filesCommitted:e.filesCommitted}),b.info("User changes committed before batch operation",{taskId:_,userCommitHash:e.commitHash?.substring(0,8),userFilesCommitted:e.filesCommitted}))}catch(e){b.warn("Pre-tool user changes commit failed",{taskId:_,error:e instanceof Error?e.message:e+""})}Date.now(),M=Date.now(),C=d.FileOperationPhase.RECORD_CREATION,a.incrementCounter("replace_in_files_phase",1,{phase:C})
|
|
5069
|
+
const{toolRecordId:A}=await d.createFileOperationRecords(_,j,t.projectId,"replace-in-files",P,{operationCount:E.length,totalReplacements:E.reduce(((e,t)=>e+t.replacements.length),0),globalFuzzyMatch:q,userComment:S},r,o,b,a,"replace_in_files",c)
|
|
5070
|
+
v=A,Date.now(),M=Date.now(),C=d.FileOperationPhase.STRING_REPLACEMENT,a.incrementCounter("replace_in_files_phase",1,{phase:C})
|
|
5285
5071
|
const F=[],N=[]
|
|
5286
5072
|
for(const e of E){const r=e.path?D.get(e.path):void 0,o=await n(e,q,t,0,0,r?.message,r?.debugInfo)
|
|
5287
|
-
F.push(o),o.successfulReplacements>0&&"file"===o.type&&o.path&&N.push(o.path)}Date.now(),
|
|
5073
|
+
F.push(o),o.successfulReplacements>0&&"file"===o.type&&o.path&&N.push(o.path)}Date.now(),M=Date.now()
|
|
5288
5074
|
const L=E.filter((e=>e.path&&!e.documentId)).map((e=>({path:e.path}))),z=await d.handleMultiFileGitCommit(_,L,F,N.length,{operationType:"Replace in files",toolRecordId:A||v||"unknown",successField:"successfulReplacements",logger:b,metrics:a,metricsPrefix:"replace_in_files"},t),B=z.commitHash
|
|
5289
5075
|
Date.now(),Date.now()
|
|
5290
|
-
const H=F.filter((e=>e.success)).length,U=F.length-H,
|
|
5291
|
-
await o.updateToolRecord(v,{metadata:{path:
|
|
5076
|
+
const H=F.filter((e=>e.success)).length,U=F.length-H,G=F.reduce(((e,t)=>e+t.successfulReplacements),0),W=F.reduce(((e,t)=>e+t.failedReplacements),0),V=F.map((e=>({type:e.type,path:e.path,documentId:e.documentId,filename:e.filename,replacements:e.replacements.map((e=>({old_str:e.old,new_str:e.new,success:e.success,error:e.error,matchesFound:e.matchesFound,matchType:e.matchType,lines:e.lines})))}))),J=F.filter((e=>e.success)).map((e=>({path:e.path,documentId:e.documentId,filename:e.filename,successfulReplacements:e.successfulReplacements,failedReplacements:e.failedReplacements}))),K=F.filter((e=>!e.success)).map((e=>({path:e.path,documentId:e.documentId,filename:e.filename,error:e.error,successfulReplacements:e.successfulReplacements,failedReplacements:e.failedReplacements})))
|
|
5077
|
+
await o.updateToolRecord(v,{metadata:{path:P,status:0===U?"completed":"partial",operationCount:E.length,operations:V,successfulFiles:J,failedFiles:K,successfulReplacements:G,failedReplacements:W,processingTime:Date.now()-I,userComment:S,...z.success&&z.commitHash&&{commitHash:z.commitHash,previousCommitHash:z.previousCommitHash||void 0}}})
|
|
5292
5078
|
const Y=await async function(e,t,r,n,o,s){const i=e.filter((e=>e.success)).length,a=e.length-i,c=e.filter((e=>!e.success&&!e.error&&e.successfulReplacements>0)).length
|
|
5293
5079
|
let l="## Replace In Files - Batch Results\n\n"
|
|
5294
5080
|
if(o.getCurrentBranchContext)try{const e=await o.getCurrentBranchContext()
|
|
@@ -5300,8 +5086,8 @@ if(o.length>0){l+="\n**Successful Replacements:**\n"
|
|
|
5300
5086
|
for(const e of o)l+=`- \u2705 \`${e.old.substring(0,40)}${e.old.length>40?"...":""}\` \u2192 \`${e.new.substring(0,40)}${e.new.length>40?"...":""}\``,e.matchesFound&&(l+=` (${e.matchesFound} occurrence${e.matchesFound>1?"s":""})`),e.lines&&e.lines.length>0&&3>=e.lines.length?l+=` at line${e.lines.length>1?"s":""} ${e.lines.join(", ")}`:e.lines&&e.lines.length>3&&(l+=` at ${e.lines.length} locations`),l+="\n"}const s=r.replacements.filter((e=>!e.success))
|
|
5301
5087
|
if(s.length>0){l+="\n**Failed Replacement Details:**\n"
|
|
5302
5088
|
for(const e of s)l+=`- \u274c \`${e.old.substring(0,40)}${e.old.length>40?"...":""}\` \u2192 \`${e.new.substring(0,40)}${e.new.length>40?"...":""}\`: ${e.error}\n`,e.details&&e.details.length>0&&(l+=" **Candidates found:**\n",l+=e.details.slice(0,5).map((e=>` - Line ${e.line}: \`${e.actually_matched.substring(0,40)}${e.actually_matched.length>40?"...":""}\` (${e.match_type})`)).join("\n")+"\n",e.details.length>5&&(l+=` ... and ${e.details.length-5} more matches\n`)),e.similarMatches&&e.similarMatches.length>0&&(l+=" **Did you mean? (Similar matches found):**\n",l+=e.similarMatches.map((e=>` - Line ${e.line}: \`${e.text.substring(0,60)}${e.text.length>60?"...":""}\` (${e.reason}, similarity: ${(100*e.similarity).toFixed(0)}%)`)).join("\n")+"\n")}l+="\n"}const u=e.filter((e=>"document"===e.type&&(e.success||e.successfulReplacements>0)))
|
|
5303
|
-
return u.length>0&&(l+=`\n**Document Changes:** ${u.length} modified document(s) synced back to tracking system.\n`),o.workspaceManager?.largeFileWarning&&(l+=o.workspaceManager.largeFileWarning,o.workspaceManager.largeFileWarning=""),l}(F,B,W,
|
|
5304
|
-
return{content:[{type:"text",text:Y}],isError:0===
|
|
5089
|
+
return u.length>0&&(l+=`\n**Document Changes:** ${u.length} modified document(s) synced back to tracking system.\n`),o.workspaceManager?.largeFileWarning&&(l+=o.workspaceManager.largeFileWarning,o.workspaceManager.largeFileWarning=""),l}(F,B,G,W,t,v)
|
|
5090
|
+
return{content:[{type:"text",text:Y}],isError:0===G}}catch(e){const t=Date.now()-I
|
|
5305
5091
|
if(b.error("Replace in files batch operation failed",{error:e instanceof Error?e.stack:e+"",duration:t,phase:C}),v)try{await o.updateToolRecord(v,{metadata:{status:"failed",error:(0,k.getErrorMessage)(e),phase:C,duration:t}})}catch(e){}return a.incrementCounter("replace_in_files_errors",1,{phase:C}),{content:[{type:"text",text:"\u274c **Replace In Files Failed:** "+(0,k.getErrorMessage)(e)}],isError:!0}}}
|
|
5306
5092
|
const l=c(t(1943)),u=(a(t(9896)),a(t(6928)),c(t(6982)),t(6183)),d=a(t(5967)),h=t(3626),g=t(9860),p=t(5003),f=t(7478),m=t(9949),y=t(9947),w=t(1318),k=t(8824)},9470(e,exports){"use strict"
|
|
5307
5093
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.parseLineSpec=function(e){if(!e||""===e.trim())throw Error("Line specification cannot be empty")
|
|
@@ -5341,87 +5127,7 @@ Object.defineProperty(exports,"Server",{enumerable:!0,get(){return r.Server}})
|
|
|
5341
5127
|
const n=t(5802)
|
|
5342
5128
|
Object.defineProperty(exports,"StdioServerTransport",{enumerable:!0,get(){return n.StdioServerTransport}})
|
|
5343
5129
|
const o=t(2422)
|
|
5344
|
-
Object.defineProperty(exports,"SSEServerTransport",{enumerable:!0,get(){return o.SSEServerTransport}})},
|
|
5345
|
-
var r=this&&this.__importDefault||function(e){return e&&e.__esModule?e:{default:e}}
|
|
5346
|
-
Object.defineProperty(exports,"__esModule",{value:!0}),exports.SingleAgentWorkspaceManager=void 0
|
|
5347
|
-
const n=r(t(6928)),o=t(8824),s=t(7075),i=t(1387),a=t(9013)
|
|
5348
|
-
exports.SingleAgentWorkspaceManager=class{constructor(e,t,r,n){this.basePath=e,this.logger=t,this.git=r,this.metrics=n,this.currentRequestId=null,this.currentBranch="main",this.readonlyBranchCheckDone=!1,this.workspaceKnownClean=!1,this.largeFileWarning=""
|
|
5349
|
-
const o=s.ConflictResolutionUtils.initializeDetectors(r,t,n)
|
|
5350
|
-
this.conflictDetector=o.conflictDetector,this.safetyAnalyzer=o.safetyAnalyzer,this.conflictResolver=o.conflictResolver,this.gitAdapter=new a.BranchGitAdapter(this.basePath,r,this.conflictDetector,t,n),this.requestProcessor=new i.WorkspaceRequestProcessor(this.gitAdapter,this.conflictDetector,this.safetyAnalyzer,this.conflictResolver,t),this.initializeCurrentBranch()}setTaskCreator(e){this.taskCreator=e}async initializeCurrentBranch(){try{const e=process.env.ALCHEMY_INITIAL_BRANCH
|
|
5351
|
-
if(e){this.logger.info("ALCHEMY_INITIAL_BRANCH set, switching to branch without locking",{initialBranch:e})
|
|
5352
|
-
try{const t=await this.git.branch()
|
|
5353
|
-
if(t.all.includes(e)||t.all.includes("remotes/origin/"+e.replace("refs/heads/",""))){await this.git.checkout(e),this.currentBranch=e
|
|
5354
|
-
const t=e.match(/^requests\/(.+)$/)
|
|
5355
|
-
return t&&(this.currentRequestId=t[1]),void this.logger.info("Successfully switched to initial branch (readonly mode)",{currentBranch:this.currentBranch,currentRequestId:this.currentRequestId})}this.logger.warn("ALCHEMY_INITIAL_BRANCH specified but branch does not exist",{initialBranch:e})}catch(t){this.logger.warn("Failed to switch to ALCHEMY_INITIAL_BRANCH",{initialBranch:e,error:t})}}if(this.currentBranch=await this.git.revparse(["--abbrev-ref","HEAD"]),this.currentBranch.startsWith("requests/")){const e=this.currentBranch.match(/^requests\/(.+)$/)
|
|
5356
|
-
e&&(this.currentRequestId=e[1])}this.logger.debug("Initialized single-agent workspace manager",{currentBranch:this.currentBranch,currentRequestId:this.currentRequestId})}catch(e){this.logger.warn("Failed to initialize current branch, defaulting to main",{error:e}),this.currentBranch="main",this.currentRequestId=null}}async initializeRequest(e,t){const r=Date.now(),n=s.WorkspaceValidation.validateRequestId(e)
|
|
5357
|
-
if(!n.isValid)throw Error("Invalid request ID: "+n.errors.join(", "))
|
|
5358
|
-
const i="requests/"+n.sanitized
|
|
5359
|
-
try{s.WorkspaceLogging.logOperation(this.logger,"info","Initializing request by creating branch",e,"single-agent","initializeRequest",{requestTitle:t,branchName:i,architecture:"hybrid-creation"})
|
|
5360
|
-
const n=(await this.git.branch()).all.includes(i)
|
|
5361
|
-
if(n)s.WorkspaceLogging.logOperation(this.logger,"info","Branch already exists, skipping creation",e,"single-agent","initializeRequest",{branchName:i})
|
|
5362
|
-
else{const t=await this.git.revparse(["--abbrev-ref","HEAD"]),r=await this.gitAdapter.branchManager.getBaseBranch()
|
|
5363
|
-
await this.git.checkout(["-b",i,r]),await this.git.checkout(t),s.WorkspaceLogging.logOperation(this.logger,"info","Created branch and returned to original",e,"single-agent","initializeRequest",{branchName:i,baseBranch:r,returnedTo:t})}const o=Date.now()-r
|
|
5364
|
-
this.metrics.recordValue("workspace.initialize",o),s.WorkspaceLogging.logOperation(this.logger,"info","Successfully initialized request with branch",e,"single-agent","initializeRequest",{branchName:i,existed:n,duration:o,architecture:"hybrid-creation"})}catch(t){const n=Date.now()-r
|
|
5365
|
-
throw this.metrics.recordValue("workspace.initialize",n),s.WorkspaceLogging.logOperation(this.logger,"error","Failed to initialize request",e,"single-agent","initializeRequest",{error:(0,o.getErrorMessage)(t),duration:n}),t}}async ensureWorkspaceReady(e,t){const r=Date.now(),n=s.WorkspaceValidation.validateRequestId(e)
|
|
5366
|
-
if(!n.isValid)throw Error("Invalid request ID: "+n.errors.join(", "))
|
|
5367
|
-
const i=n.sanitized,a="requests/"+i,c=await this.git.revparse(["--abbrev-ref","HEAD"])
|
|
5368
|
-
if(c===a)return this.currentRequestId=i,this.currentBranch=a,void this.logger.debug("Workspace already ready",{requestId:i,currentBranch:this.currentBranch})
|
|
5369
|
-
try{if(s.WorkspaceLogging.logOperation(this.logger,"info","Ensuring workspace ready by switching to branch",e,"single-agent","ensureWorkspaceReady",{currentBranch:c,targetBranch:a,architecture:"hybrid-creation"}),!(await this.git.branch()).all.includes(a))throw Error(`Branch ${a} does not exist. Was initializeRequest() called?`)
|
|
5370
|
-
try{await this.switchToRequest(i)}catch(t){s.WorkspaceLogging.logOperation(this.logger,"warn","switchToRequest failed, trying direct checkout",e,"single-agent","ensureWorkspaceReady",{error:t instanceof Error?t.message:t+"",attempting:"direct-checkout",branchName:a}),await this.git.checkout(a),this.currentRequestId=i,this.currentBranch=a,s.WorkspaceLogging.logOperation(this.logger,"info","Direct checkout succeeded",e,"single-agent","ensureWorkspaceReady",{branchName:a})}const t=Date.now()-r
|
|
5371
|
-
this.metrics.recordValue("workspace.ensure_ready",t),s.WorkspaceLogging.logOperation(this.logger,"info","Workspace is ready",e,"single-agent","ensureWorkspaceReady",{branchName:this.currentBranch,duration:t,architecture:"hybrid-creation"})}catch(t){const n=Date.now()-r
|
|
5372
|
-
throw this.metrics.recordValue("workspace.ensure_ready",n),s.WorkspaceLogging.logOperation(this.logger,"error","Failed to ensure workspace ready",e,"single-agent","ensureWorkspaceReady",{error:(0,o.getErrorMessage)(t),duration:n}),t}}async switchToRequest(e,t){const r=Date.now(),n=this.getCurrentContext(),i=s.WorkspaceValidation.validateRequestId(e)
|
|
5373
|
-
if(!i.isValid){const t="Invalid request ID: "+i.errors.join(", ")
|
|
5374
|
-
throw s.WorkspaceLogging.logOperation(this.logger,"error",t,e,"single-agent","switchToRequest"),Error(t)}const a=i.sanitized
|
|
5375
|
-
try{s.WorkspaceLogging.logOperation(this.logger,"info","Switching to request (assuming branch exists)",e,"single-agent","switchToRequest",{previousBranch:n.branchName,architecture:"aligned-with-multi-agent"})
|
|
5376
|
-
const t=await this.gitAdapter.setupWorkspace(a)
|
|
5377
|
-
this.currentRequestId=t.requestId,this.currentBranch=t.branchName
|
|
5378
|
-
const o=Date.now()-r
|
|
5379
|
-
return this.metrics.recordValue("workspace.switch",o),s.WorkspaceLogging.logOperation(this.logger,"info","Successfully switched to request",e,"single-agent","switchToRequest",{branchName:t.branchName,previousBranch:n.branchName,duration:o,architecture:"aligned-with-multi-agent"}),{success:!0,message:"Switched to request "+a,previousContext:n,newContext:this.getCurrentContext()}}catch(t){const n=Date.now()-r
|
|
5380
|
-
this.metrics.recordValue("workspace.switch",n)
|
|
5381
|
-
const i=(0,o.getErrorMessage)(t),a=i.includes("does not exist"),c=a?`Branch for request ${e} does not exist. Use initializeRequest() first to create the branch.`:`Failed to switch to request ${e}: ${i}`
|
|
5382
|
-
throw s.WorkspaceLogging.logOperation(this.logger,"error","Failed to switch to request",e,"single-agent","switchToRequest",{error:i,isMissingBranch:a,duration:n,suggestion:a?"Call initializeRequest() first":"Check branch status"}),new s.ConflictDetectionError(c,"single-agent-switch-"+e,[])}}async switchToMain(e){const t=Date.now(),r=this.getCurrentContext()
|
|
5383
|
-
try{const e=await this.gitAdapter.branchManager.getBaseBranch(),n=await this.gitAdapter.branchManager.switchToBranch(e)
|
|
5384
|
-
if(!n.success)throw Error("Failed to switch to main branch: "+n.error)
|
|
5385
|
-
this.currentBranch=e,this.currentRequestId=null
|
|
5386
|
-
const o=Date.now()-t
|
|
5387
|
-
return this.metrics.recordValue("workspace.switch_main",o),s.WorkspaceLogging.logOperation(this.logger,"info","Successfully switched to main branch",null,"single-agent","switchToMain",{mainBranch:e,previousBranch:r.branchName,duration:o,architecture:"aligned-with-multi-agent"}),{success:!0,message:"Switched to "+e,previousContext:r,newContext:this.getCurrentContext()}}catch(e){const r=Date.now()-t
|
|
5388
|
-
throw this.metrics.recordValue("workspace.switch_main",r),s.WorkspaceLogging.logOperation(this.logger,"error","Failed to switch to main branch",null,"single-agent","switchToMain",{error:(0,o.getErrorMessage)(e),duration:r}),new s.ConflictDetectionError("Failed to switch to main: "+(0,o.getErrorMessage)(e),"single-agent",[])}}async commitChanges(e,t){const r=Date.now()
|
|
5389
|
-
try{t&&t.length>0?await this.git.add(t):await this.git.add("."),await this.git.commit(e)
|
|
5390
|
-
const n=await this.git.revparse(["HEAD"]),o=Date.now()-r
|
|
5391
|
-
return this.metrics.recordValue("workspace.commit",o),this.logger.info("Successfully committed changes",{message:e,commitHash:n.substring(0,8),filesCount:t?.length||"all",duration:o}),{hash:n,message:e,files:t||[]}}catch(t){const n=Date.now()-r
|
|
5392
|
-
throw this.metrics.recordValue("workspace.commit",n),this.logger.error("Failed to commit changes",{message:e,error:(0,o.getErrorMessage)(t),duration:n}),new s.ConflictDetectionError("Failed to commit changes: "+(0,o.getErrorMessage)(t),"single-agent-commit",[])}}async completeRequest(e,t,r){const n=Date.now()
|
|
5393
|
-
try{s.WorkspaceLogging.logOperation(this.logger,"info","Starting request completion (refactored)",e,"single-agent","completeRequest",{requestTitle:t,skipConflictDetection:r?.skipConflictDetection||!1,architecture:"shared-processor"})
|
|
5394
|
-
const o=await this.requestProcessor.completeRequest(e,t,{skipConflictDetection:r?.skipConflictDetection||!1}),i=Date.now()-n
|
|
5395
|
-
return this.metrics.recordValue("workspace.complete",i),s.WorkspaceLogging.logOperation(this.logger,"info","Request completion successful (refactored)",e,"single-agent","completeRequest",{mergeCommitHash:o.mergeCommitHash.substring(0,8),mergedFiles:o.mergedFiles?.length||0,cleanedUp:o.cleanedUp,wasAutoMerged:o.autoMergeInfo?.wasAutoMerged,strategy:o.autoMergeInfo?.strategy,duration:i,architecture:"shared-processor"}),o}catch(t){const r=Date.now()-n
|
|
5396
|
-
throw this.metrics.recordValue("workspace.complete",r),s.WorkspaceLogging.logOperation(this.logger,"error","Request completion failed (refactored)",e,"single-agent","completeRequest",{error:(0,o.getErrorMessage)(t),duration:r,architecture:"shared-processor"}),t}}resolveFilePath(e,t){return n.default.resolve(this.basePath,e)}async createCommit(e,t,r){return await this.commitChanges(e,t)}async cancelRequest(e){const t=s.WorkspaceValidation.validateRequestId(e)
|
|
5397
|
-
if(!t.isValid)throw Error("Invalid request ID: "+t.errors.join(", "))
|
|
5398
|
-
const r="requests/"+t.sanitized
|
|
5399
|
-
try{s.WorkspaceLogging.logOperation(this.logger,"info","Cancelling request (deleting branch)",e,"single-agent","cancelRequest",{branchName:r,architecture:"aligned-with-multi-agent"}),this.currentBranch===r&&await this.switchToMain(),await this.git.deleteLocalBranch(r),s.WorkspaceLogging.logOperation(this.logger,"info","Successfully cancelled request",e,"single-agent","cancelRequest",{branchName:r,switchedToMain:this.currentBranch!==r})}catch(t){throw s.WorkspaceLogging.logOperation(this.logger,"error","Failed to cancel request",e,"single-agent","cancelRequest",{branchName:r,error:(0,o.getErrorMessage)(t)}),t}}async listActiveWorkspaces(){try{return(await this.git.branch()).all.filter((e=>e.startsWith("requests/"))).map((e=>({requestId:e.replace("requests/",""),path:this.basePath,branchName:e,isActive:this.currentBranch===e,created:new Date,lastAccessed:new Date})))}catch(e){return this.logger.error("Failed to list active workspaces",{error:(0,o.getErrorMessage)(e)}),[]}}getCurrentContext(e){return{requestId:this.currentRequestId,basePath:this.basePath,branchName:this.currentBranch,isMainBranch:"main"===this.currentBranch||"master"===this.currentBranch,mode:"single-agent"}}async getWorkspaceInfo(e){try{const t=s.WorkspaceValidation.validateRequestId(e)
|
|
5400
|
-
if(!t.isValid)return null
|
|
5401
|
-
const r=t.sanitized,n="requests/"+r,o=await this.git.branch()
|
|
5402
|
-
return o.all.includes(n)||o.all.includes("remotes/origin/"+n)?{requestId:r,path:this.basePath,branchName:n,isActive:this.currentBranch===n,created:new Date,lastAccessed:new Date}:null}catch(t){return this.logger.error("Failed to get workspace info",{requestId:e,error:(0,o.getErrorMessage)(t)}),null}}getMainGit(){return this.gitAdapter.getMainGit()}async getWorktreeInfo(e){}getCurrentGit(e){return this.git}async ensureReadonlyBranchIfNeeded(e,t,r,n){if(!this.readonlyBranchCheckDone){this.readonlyBranchCheckDone=!0
|
|
5403
|
-
try{const e=n
|
|
5404
|
-
if(!e)return void this.logger.debug("No sessionId available for readonly check")
|
|
5405
|
-
this.logger.debug("Checking readonly branch for session",{sessionId:e,toolName:t})
|
|
5406
|
-
const o=r?.getCLISessionClient?.()
|
|
5407
|
-
if(!o)return void this.logger.debug("No CLI session client available for readonly check")
|
|
5408
|
-
const s=await o.getByExternalId(e)
|
|
5409
|
-
if(!s?.agentType)return void this.logger.debug("No agent type found for session",{sessionId:e})
|
|
5410
|
-
this.logger.debug("Found session agent type",{sessionId:e,agentType:s.agentType})
|
|
5411
|
-
const i=await this.fetchAgentConfig(s.agentType)
|
|
5412
|
-
if(!i||"readonly"!==i.requestContextMode)return void this.logger.debug("Agent does not have readonly requestContextMode",{agentType:s.agentType})
|
|
5413
|
-
this.logger.debug("Agent has readonly requestContextMode",{agentType:s.agentType})
|
|
5414
|
-
const a=r?.getSessionRequestAssociationClient?.()
|
|
5415
|
-
if(!a)return void this.logger.debug("No session association client available")
|
|
5416
|
-
const c=await a.getActiveRequestsForSession(e,!0)
|
|
5417
|
-
if(0===c.length)return void this.logger.debug("No active request association found for session",{sessionId:e})
|
|
5418
|
-
const l=c[0].requestLocalId,u="requests/"+l
|
|
5419
|
-
this.logger.info("Readonly agent with request association, switching to branch without locking",{sessionId:e,agentType:s.agentType,requestId:l,readonlyBranch:u})
|
|
5420
|
-
const d=await this.git.branch()
|
|
5421
|
-
d.all.includes(u)||d.all.includes("remotes/origin/"+u)?(await this.git.checkout(u),this.currentBranch=u,this.currentRequestId=l,this.logger.info("Successfully switched to readonly branch",{currentBranch:this.currentBranch,currentRequestId:this.currentRequestId})):this.logger.warn("Readonly branch does not exist",{readonlyBranch:u})}catch(e){this.logger.debug("Error during readonly branch check",{error:(0,o.getErrorMessage)(e)})}}}async fetchAgentConfig(e){try{const t="http://localhost:3456/api/agents/by-name/"+encodeURIComponent(e),r=await fetch(t)
|
|
5422
|
-
if(!r.ok)return null
|
|
5423
|
-
const n=await r.json()
|
|
5424
|
-
return n.success?n.data??null:null}catch{return null}}async cleanup(){this.logger.info("Cleaning up single-agent workspace manager")}}},9671(e,exports){"use strict"
|
|
5130
|
+
Object.defineProperty(exports,"SSEServerTransport",{enumerable:!0,get(){return o.SSEServerTransport}})},9671(e,exports){"use strict"
|
|
5425
5131
|
Object.defineProperty(exports,"__esModule",{value:!0}),exports.findPreviousCommit=async function(e,t,r){try{if(!r){const r=await e.raw(["rev-list","--max-count=1","HEAD","--",t])
|
|
5426
5132
|
return r&&r.trim()?r.trim():null}const n=await e.raw(["rev-list","--max-count=1",r+"^","--",t])
|
|
5427
5133
|
return n&&n.trim()?n.trim():null}catch(e){return null}}},9697(e,exports,t){"use strict"
|
|
@@ -5608,7 +5314,14 @@ return c.length>0&&(e+=`**Locked Documents (${c.length}):**\n`,c.forEach((t=>{co
|
|
|
5608
5314
|
e+=`- \`${t.documentId}\` (locked ${r} by ${t.lockedByUserId||"unknown user"})\n`})),e+="\n"),l.length>0&&(e+=`**Validation Errors (${l.length}):**\n`,l.forEach((t=>{e+=`- ${t}\n`})),e+="\n"),e+="**Resolution:**\n",e+="- Unlock any locked documents before proceeding\n",e+="- Resolve any validation errors\n",e+="- Try the operation again",a.warn("Batch operation blocked due to locked documents or errors",{lockedCount:c.length,errorCount:l.length}),{isValid:!1,error:e}}return a.debug("All documents validated successfully for batch operation"),{isValid:!0}}Object.defineProperty(exports,"__esModule",{value:!0}),exports.validateDocumentNotLocked=r,exports.validateDocumentsNotLocked=n,exports.ensureDocumentNotLocked=async function(e,t,n,s,i){const a=await r(e,t,n,s,i)
|
|
5609
5315
|
if(!a.isValid)throw new o.ValidationError(a.error||"Document is locked")},exports.ensureDocumentsNotLocked=async function(e,t,r,s,i){const a=await n(e,t,r,s,i)
|
|
5610
5316
|
if(!a.isValid)throw new o.ValidationError(a.error||"One or more documents are locked")}
|
|
5611
|
-
const o=t(9860),s=t(8824)}
|
|
5317
|
+
const o=t(9860),s=t(8824)},9968(e,exports,t){"use strict"
|
|
5318
|
+
Object.defineProperty(exports,"__esModule",{value:!0}),exports.handleUpdateSpecialization=async function(e,t,o,s){const i=r.UpdateSpecializationSchema.parse(e),{specialization:a}=i
|
|
5319
|
+
if(!s?.sessionId)return{content:[{type:"text",text:"Cannot update specialization: session identity not available."}],isError:!0}
|
|
5320
|
+
if(!o)return{content:[{type:"text",text:"Cannot update specialization: API client not available."}],isError:!0}
|
|
5321
|
+
const c=o.getCLISessionClient()
|
|
5322
|
+
if(!c)return{content:[{type:"text",text:"Cannot update specialization: session client not available."}],isError:!0}
|
|
5323
|
+
try{return await c.createOrUpdateSession({externalSessionId:s.sessionId,specialization:a}),t.info("Specialization updated",{sessionId:s.sessionId,specialization:a}),{content:[{type:"text",text:"Specialization updated to: "+a}]}}catch(e){return t.error("Failed to update specialization",{sessionId:s.sessionId,error:(0,n.getErrorMessage)(e)}),{content:[{type:"text",text:"Failed to update specialization: "+(0,n.getErrorMessage)(e)}],isError:!0}}}
|
|
5324
|
+
const r=t(6183),n=t(8824)}},s={}
|
|
5612
5325
|
e.m=o,r=Object.getPrototypeOf?e=>Object.getPrototypeOf(e):e=>e.__proto__,e.t=function(n,o){if(1&o&&(n=this(n)),8&o)return n
|
|
5613
5326
|
if("object"==typeof n&&n){if(4&o&&n.__esModule)return n
|
|
5614
5327
|
if(16&o&&"function"==typeof n.then)return n}var s=Object.create(null)
|