@@ -24,7 +24,7 @@ export const AgentConfigSchema = z.object({
2424 . array ( z . string ( ) )
2525 . nullish ( )
2626 . describe (
27- "List of tool identifiers that this agent type can utilize. Null/undefined means all available." ,
27+ "List of tool identifiers that this agent type can utilize. Null/undefined means all available. Empty array means no tools. " ,
2828 ) ,
2929 maxPoolSize : z
3030 . number ( )
@@ -45,7 +45,7 @@ export type AgentConfig = z.infer<typeof AgentConfigSchema>;
4545 */
4646export const AgentSchema = z . object ( {
4747 /** Unique identifier for this specific agent instance */
48- id : z . string ( ) ,
48+ agentId : z . string ( ) ,
4949 /** The type of agent this instance represents */
5050 type : z . string ( ) ,
5151 kind : AgentKindSchema ,
@@ -59,6 +59,9 @@ export const AgentSchema = z.object({
5959 instance : z . any ( ) ,
6060} ) ;
6161export type Agent = z . infer < typeof AgentSchema > ;
62+ export type AgentWithInstance < TAgentInstance > = Omit < Agent , "instance" > & {
63+ instance : TAgentInstance ;
64+ } ;
6265
6366/**
6467 * Schema for an available tool.
@@ -99,13 +102,13 @@ export interface AgentLifecycleCallbacks<TAgentInstance> {
99102 * @param config - Configuration for the agent
100103 * @param poolStats - Statistics of the agent pool
101104 * @param toolsFactory - Factory to create tools
102- * @returns Promise resolving to the new agent's ID
105+ * @returns Promise resolving to the new agent's id and instance
103106 */
104107 onCreate : (
105108 config : AgentConfig ,
106109 poolStats : PoolStats ,
107110 toolsFactory : BaseToolsFactory ,
108- ) => Promise < { id : string ; instance : TAgentInstance } > ;
111+ ) => Promise < { agentId : string ; instance : TAgentInstance } > ;
109112
110113 /**
111114 * Called when an agent is being destroyed
@@ -135,13 +138,6 @@ export interface AgentInstanceRef<TInstance> {
135138 instance : TInstance ;
136139}
137140
138- function ref < TAgentInstance > (
139- agentId : string ,
140- instance : TAgentInstance ,
141- ) : AgentInstanceRef < TAgentInstance > {
142- return { agentId, instance } ;
143- }
144-
145141/**
146142 * Registry for managing agent types, instances, and pools.
147143 * Provides functionality for:
@@ -158,12 +154,10 @@ export class AgentRegistry<TAgentInstance> {
158154 private readonly logger : Logger ;
159155 /** Map of registered agent kind and their configurations */
160156 private agentConfigs : Map < AgentKind , AgentConfigMap > ;
161- /** Map of all active agent instances */
162- private activeAgents = new Map < string , Agent > ( ) ;
157+ /** Map of all agent instances */
158+ private agents = new Map < string , Agent > ( ) ;
163159 /** Map of agent pools by kind and type, containing sets of available agent IDs */
164160 private agentPools : Map < AgentKind , AgentTypePoolMap > ;
165- /** Map of agent instances available by agent IDs */
166- private agentInstances = new Map < string , TAgentInstance > ( ) ;
167161 /** Callbacks for agent lifecycle events */
168162 private callbacks : AgentLifecycleCallbacks < TAgentInstance > ;
169163 /** Maps of tools factories for use by agents per agent kinds */
@@ -249,7 +243,7 @@ export class AgentRegistry<TAgentInstance> {
249243
250244 const toolsFactory = this . getToolsFactory ( config . kind ) ;
251245 const availableTools = toolsFactory . getAvailableTools ( ) ;
252- if ( config . tools ) {
246+ if ( config . tools ?. filter ( ( it ) => ! ! it . length ) . length ) {
253247 const undefinedTools = config . tools . filter (
254248 ( tool ) => ! availableTools . some ( ( at ) => at . name === tool ) ,
255249 ) ;
@@ -314,7 +308,8 @@ export class AgentRegistry<TAgentInstance> {
314308 } ) ;
315309
316310 for ( let i = 0 ; i < needed ; i ++ ) {
317- const { agentId : agentId } = await this . createAgent ( kind , type , true ) ;
311+ const agent = await this . createAgent ( kind , type , true ) ;
312+ const { agentId } = agent ;
318313 pool . add ( agentId ) ;
319314 this . logger . trace ( "Added agent to pool" , { kind, type, agentId } ) ;
320315 }
@@ -353,7 +348,7 @@ export class AgentRegistry<TAgentInstance> {
353348 * @returns Promise resolving to the agent ID
354349 * @throws Error if no agents are available and pool is at capacity
355350 */
356- async acquireAgent ( kind : AgentKind , type : string ) : Promise < AgentInstanceRef < TAgentInstance > > {
351+ async acquireAgent ( kind : AgentKind , type : string ) : Promise < AgentWithInstance < TAgentInstance > > {
357352 this . logger . debug ( "Attempting to acquire agent" , { type } ) ;
358353 const config = this . getAgentTypeConfig ( kind , type ) ;
359354 const pool = this . getAgentPoolMap ( kind , type ) ;
@@ -365,7 +360,7 @@ export class AgentRegistry<TAgentInstance> {
365360
366361 // Try to get an available agent from the pool
367362 for ( const agentId of pool ) {
368- const agent = this . activeAgents . get ( agentId ) ;
363+ const agent = this . agents . get ( agentId ) ;
369364 if ( agent && ! agent . inUse ) {
370365 pool . delete ( agentId ) ;
371366 agent . inUse = true ;
@@ -377,7 +372,7 @@ export class AgentRegistry<TAgentInstance> {
377372 await this . callbacks . onAcquire ( agentId ) ;
378373 }
379374
380- return ref ( agentId , agent . instance ) ;
375+ return agent as AgentWithInstance < TAgentInstance > ;
381376 }
382377 }
383378
@@ -406,7 +401,7 @@ export class AgentRegistry<TAgentInstance> {
406401 */
407402 async releaseAgent ( agentId : string ) : Promise < void > {
408403 this . logger . debug ( "Attempting to release agent" , { agentId } ) ;
409- const agent = this . activeAgents . get ( agentId ) ;
404+ const agent = this . agents . get ( agentId ) ;
410405 if ( ! agent ) {
411406 this . logger . error ( "Agent not found for release" , { agentId } ) ;
412407 throw new Error ( `Agent with ID '${ agentId } ' not found` ) ;
@@ -443,28 +438,25 @@ export class AgentRegistry<TAgentInstance> {
443438 kind : AgentKind ,
444439 type : string ,
445440 forPool : boolean ,
446- ) : Promise < AgentInstanceRef < TAgentInstance > > {
441+ ) : Promise < AgentWithInstance < TAgentInstance > > {
447442 this . logger . debug ( "Creating new agent" , { kind, type, forPool } ) ;
448443 const config = this . getAgentTypeConfig ( kind , type ) ;
449444 const poolStats = this . getPoolStats ( kind , type ) ;
450445 const toolsFactory = this . getToolsFactory ( kind ) ;
451- const { id : agentId , instance } = await this . callbacks . onCreate (
452- config ,
453- poolStats ,
454- toolsFactory ,
455- ) ;
446+ const { agentId, instance } = await this . callbacks . onCreate ( config , poolStats , toolsFactory ) ;
456447
457- this . activeAgents . set ( agentId , {
458- id : agentId ,
448+ const agent = {
449+ agentId,
459450 kind,
460451 type,
461452 config,
462453 inUse : ! forPool ,
463454 instance,
464- } ) ;
455+ } satisfies Agent ;
456+ this . agents . set ( agentId , agent ) ;
465457
466458 this . logger . info ( "Agent created successfully" , { agentId, type, forPool } ) ;
467- return ref ( agentId , instance ) ;
459+ return agent ;
468460 }
469461
470462 /**
@@ -474,7 +466,7 @@ export class AgentRegistry<TAgentInstance> {
474466 */
475467 async destroyAgent ( agentId : string ) : Promise < void > {
476468 this . logger . debug ( "Attempting to destroy agent" , { agentId } ) ;
477- const agent = this . activeAgents . get ( agentId ) ;
469+ const agent = this . agents . get ( agentId ) ;
478470 if ( ! agent ) {
479471 this . logger . error ( "Agent not found for destruction" , { agentId } ) ;
480472 throw new Error ( `Agent with ID '${ agentId } ' not found` ) ;
@@ -488,7 +480,7 @@ export class AgentRegistry<TAgentInstance> {
488480 }
489481
490482 await this . callbacks . onDestroy ( agent . instance ) ;
491- this . activeAgents . delete ( agentId ) ;
483+ this . agents . delete ( agentId ) ;
492484 this . logger . info ( "Agent destroyed successfully" , {
493485 agentId,
494486 kind : agent . kind ,
@@ -502,7 +494,7 @@ export class AgentRegistry<TAgentInstance> {
502494 */
503495 getActiveAgents ( ) : Agent [ ] {
504496 this . logger . trace ( "Getting active agents" ) ;
505- return Array . from ( this . activeAgents . values ( ) ) ;
497+ return Array . from ( this . agents . values ( ) ) . filter ( ( a ) => a . inUse ) ;
506498 }
507499
508500 /**
@@ -513,7 +505,7 @@ export class AgentRegistry<TAgentInstance> {
513505 */
514506 getAgent ( agentId : string ) : Agent {
515507 this . logger . trace ( "Getting agent by ID" , { agentId } ) ;
516- const agent = this . activeAgents . get ( agentId ) ;
508+ const agent = this . agents . get ( agentId ) ;
517509 if ( ! agent ) {
518510 this . logger . error ( "Agent not found" , { agentId } ) ;
519511 throw new Error ( `Agent with ID '${ agentId } ' not found` ) ;
@@ -535,9 +527,7 @@ export class AgentRegistry<TAgentInstance> {
535527 return { poolSize : 0 , available : 0 , inUse : 0 , created : 0 } ;
536528 }
537529
538- const available = Array . from ( pool ) . filter (
539- ( agentId ) => ! this . activeAgents . get ( agentId ) ?. inUse ,
540- ) . length ;
530+ const available = Array . from ( pool ) . filter ( ( agentId ) => ! this . agents . get ( agentId ) ?. inUse ) . length ;
541531
542532 const stats = {
543533 poolSize : config . maxPoolSize ,
0 commit comments