@rowan-agent/agent 0.22.1 → 0.24.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.d.ts +63 -8
- package/dist/index.js +228 -78
- package/package.json +1 -1
package/dist/index.d.ts
CHANGED
|
@@ -319,6 +319,8 @@ declare class InMemoryExtensionHost implements ExtensionHost {
|
|
|
319
319
|
* - Tool registration support
|
|
320
320
|
*/
|
|
321
321
|
|
|
322
|
+
/** The Resource Source an Extension registration lands in: Global (`[]`) is `rowan.extensions`, any other Scope `rowan.extensions:<scopeToKey(scope)>`. */
|
|
323
|
+
declare function extensionSourceId(scope?: ScopeRef): string;
|
|
322
324
|
type ExtensionRunnerOptions = {
|
|
323
325
|
entryPhaseId?: string | null;
|
|
324
326
|
cwd?: string;
|
|
@@ -368,10 +370,12 @@ declare class ExtensionRunner {
|
|
|
368
370
|
private readonly hostUnsubscribers;
|
|
369
371
|
private readonly phases;
|
|
370
372
|
private _phaseCache;
|
|
373
|
+
private readonly skills;
|
|
371
374
|
private readonly pendingProviders;
|
|
372
375
|
private bound;
|
|
373
376
|
private readonly errorListeners;
|
|
374
377
|
private readonly capabilityListeners;
|
|
378
|
+
private readonly resourceChangeListeners;
|
|
375
379
|
/** Current agent context — set by the agent before each phase */
|
|
376
380
|
currentContext?: AgentContext;
|
|
377
381
|
constructor(options?: ExtensionRunnerOptions);
|
|
@@ -419,7 +423,7 @@ declare class ExtensionRunner {
|
|
|
419
423
|
/** Dispose all active Extensions in reverse activation order. */
|
|
420
424
|
close(): Promise<void>;
|
|
421
425
|
get extensionHost(): ExtensionHost;
|
|
422
|
-
notifyConfigChanged(extensionId: string, scope: ScopeRef): void
|
|
426
|
+
notifyConfigChanged(extensionId: string, scope: ScopeRef): Promise<void>;
|
|
423
427
|
getRunState(runId: string, extensionId: string, key: string): JsonValue | undefined;
|
|
424
428
|
setRunState(runId: string, extensionId: string, key: string, value: JsonValue): void;
|
|
425
429
|
deleteRunState(runId: string, extensionId: string, key: string): void;
|
|
@@ -437,6 +441,12 @@ declare class ExtensionRunner {
|
|
|
437
441
|
* Returns an unsubscribe function.
|
|
438
442
|
*/
|
|
439
443
|
onCapabilitiesChanged(listener: (capabilities: readonly ExtensionCapability[]) => void): () => void;
|
|
444
|
+
/**
|
|
445
|
+
* Subscribe to resource changes (tools, phases, skills registered, unregistered, or disposed).
|
|
446
|
+
* Used by RuntimeBootstrapRegistry to re-commit implicit sources after activation.
|
|
447
|
+
*/
|
|
448
|
+
onResourceChange(listener: (kind: "tool" | "phase" | "skill") => Promise<void> | void): () => void;
|
|
449
|
+
private notifyResourceChange;
|
|
440
450
|
triggerUiAction(event: {
|
|
441
451
|
contributionId: string;
|
|
442
452
|
actionId: string;
|
|
@@ -444,11 +454,14 @@ declare class ExtensionRunner {
|
|
|
444
454
|
}): void;
|
|
445
455
|
getPhase(name: string): Phase | undefined;
|
|
446
456
|
getPhases(): Phase[];
|
|
457
|
+
getRegisteredPhases(): readonly RegisteredPhase[];
|
|
447
458
|
createPhaseRegistry(input?: {
|
|
448
459
|
entryPhaseId?: string | null;
|
|
449
460
|
}): PhaseRegistry;
|
|
450
461
|
/** Adapt an extension RegisteredPhase to the core Phase type. */
|
|
451
|
-
|
|
462
|
+
adaptToPhase(reg: RegisteredPhase): Phase;
|
|
463
|
+
getSkills(): Skill[];
|
|
464
|
+
getRegisteredSkills(): readonly RegisteredSkill[];
|
|
452
465
|
/**
|
|
453
466
|
* Bind the runner — flushes pending provider registrations and
|
|
454
467
|
* replaces runtime stubs with real implementations.
|
|
@@ -489,6 +502,7 @@ declare class ExtensionRunner {
|
|
|
489
502
|
agentId?: string;
|
|
490
503
|
toolCallId?: string;
|
|
491
504
|
metadata?: Readonly<Record<string, unknown>>;
|
|
505
|
+
agentMetadata?: Readonly<Record<string, unknown>>;
|
|
492
506
|
answer?: unknown;
|
|
493
507
|
scope?: ScopeRef;
|
|
494
508
|
turn?: JsonObject;
|
|
@@ -515,6 +529,10 @@ declare class ExtensionRunner {
|
|
|
515
529
|
private registerPhaseDefinition;
|
|
516
530
|
private unregisterPhase;
|
|
517
531
|
private loadRegisteredPhase;
|
|
532
|
+
private registerSkill;
|
|
533
|
+
private registerSkillDefinition;
|
|
534
|
+
private unregisterSkill;
|
|
535
|
+
private loadRegisteredSkill;
|
|
518
536
|
private registerProvider;
|
|
519
537
|
private unregisterProvider;
|
|
520
538
|
private flushPendingProviders;
|
|
@@ -588,16 +606,22 @@ declare class RuntimeExtensionLifetime {
|
|
|
588
606
|
activate(extensions: readonly LoadedExtension[]): Promise<ExtensionActivationResult>;
|
|
589
607
|
tools(): readonly RegisteredTool[];
|
|
590
608
|
phases(): readonly Phase[];
|
|
609
|
+
registeredPhases(): readonly RegisteredPhase[];
|
|
610
|
+
skills(): readonly Skill[];
|
|
611
|
+
registeredSkills(): readonly RegisteredSkill[];
|
|
591
612
|
get extensionRunner(): ExtensionRunner;
|
|
592
613
|
get extensionHost(): ExtensionHost;
|
|
614
|
+
onResourceChange(listener: (kind: "tool" | "phase" | "skill") => Promise<void> | void): () => void;
|
|
593
615
|
dropRunState(runId: string): void;
|
|
594
616
|
close(): Promise<void>;
|
|
595
617
|
}
|
|
596
618
|
/** Bootstrap-only Registry facade; its Extension method disappears after init. */
|
|
597
619
|
declare class RuntimeBootstrapRegistry extends ResourceRegistry {
|
|
598
620
|
private readonly extensions;
|
|
599
|
-
private readonly
|
|
621
|
+
private readonly knownSources;
|
|
622
|
+
private commitQueue;
|
|
600
623
|
constructor(extensions?: RuntimeExtensionLifetime);
|
|
624
|
+
private recommit;
|
|
601
625
|
get extensionHost(): ExtensionHost;
|
|
602
626
|
/** Install Rowan-owned implicit resources before any host source is read. */
|
|
603
627
|
ensureCoreResources(): Promise<void>;
|
|
@@ -1322,8 +1346,28 @@ interface SourceInfo {
|
|
|
1322
1346
|
baseDir?: string;
|
|
1323
1347
|
displayName?: string;
|
|
1324
1348
|
}
|
|
1349
|
+
/** A loaded directory Bundle used by an extension. */
|
|
1350
|
+
type PhaseDefinition = Phase;
|
|
1325
1351
|
/** Register a Phase by directory path or Phase object; PHASE.md and direct child Skills are loaded atomically when a path is supplied. */
|
|
1326
1352
|
type PhaseRegistration = string | Phase;
|
|
1353
|
+
type RegisteredPhase = {
|
|
1354
|
+
definition: PhaseDefinition;
|
|
1355
|
+
source: {
|
|
1356
|
+
extensionPath: string;
|
|
1357
|
+
};
|
|
1358
|
+
sourceId: string;
|
|
1359
|
+
scope?: ScopeRef;
|
|
1360
|
+
};
|
|
1361
|
+
/** Register a Skill directory (containing SKILL.md) or a Skill object. Registering an existing name replaces it. */
|
|
1362
|
+
type SkillRegistration = string | Skill;
|
|
1363
|
+
type RegisteredSkill = {
|
|
1364
|
+
definition: Skill;
|
|
1365
|
+
source: {
|
|
1366
|
+
extensionPath: string;
|
|
1367
|
+
};
|
|
1368
|
+
sourceId: string;
|
|
1369
|
+
scope?: ScopeRef;
|
|
1370
|
+
};
|
|
1327
1371
|
/**
|
|
1328
1372
|
* Tool definition for registering LLM-callable tools via `api.tools.register()`.
|
|
1329
1373
|
*
|
|
@@ -1381,6 +1425,8 @@ interface ToolDefinition {
|
|
|
1381
1425
|
interface RegisteredTool {
|
|
1382
1426
|
definition: ToolDefinition;
|
|
1383
1427
|
sourceInfo: SourceInfo;
|
|
1428
|
+
sourceId: string;
|
|
1429
|
+
scope?: ScopeRef;
|
|
1384
1430
|
}
|
|
1385
1431
|
/**
|
|
1386
1432
|
* Structured extension error with attribution.
|
|
@@ -1495,9 +1541,9 @@ interface ExtensionAPI {
|
|
|
1495
1541
|
/** Tool capabilities — register and unregister custom tools. */
|
|
1496
1542
|
tools: {
|
|
1497
1543
|
/** Register a custom LLM-callable tool. */
|
|
1498
|
-
register(tool: ToolDefinition): void
|
|
1544
|
+
register(tool: ToolDefinition, scope?: ScopeRef): Promise<void>;
|
|
1499
1545
|
/** Unregister a previously registered tool by name. */
|
|
1500
|
-
unregister(toolName: string): void
|
|
1546
|
+
unregister(toolName: string, scope?: ScopeRef): Promise<void>;
|
|
1501
1547
|
};
|
|
1502
1548
|
/** Capability contributions — advertise tools or features to the host. */
|
|
1503
1549
|
capabilities: {
|
|
@@ -1514,9 +1560,9 @@ interface ExtensionAPI {
|
|
|
1514
1560
|
/** Phase execution capabilities — provides Phase In/Out, phase identity, phase routing, and registration. */
|
|
1515
1561
|
phases: {
|
|
1516
1562
|
/** Register a Phase directory bundle or Phase object. */
|
|
1517
|
-
register(phase: PhaseRegistration): Promise<void>;
|
|
1563
|
+
register(phase: PhaseRegistration, scope?: ScopeRef): Promise<void>;
|
|
1518
1564
|
/** Unregister a previously registered phase by name. */
|
|
1519
|
-
unregister(phaseName: string): void;
|
|
1565
|
+
unregister(phaseName: string, scope?: ScopeRef): Promise<void> | void;
|
|
1520
1566
|
/** Phase In: get payload from previous phase */
|
|
1521
1567
|
getPayload(): unknown;
|
|
1522
1568
|
/** Phase Out: set payload for next phase */
|
|
@@ -1532,6 +1578,13 @@ interface ExtensionAPI {
|
|
|
1532
1578
|
/** Get the message set by setMessage */
|
|
1533
1579
|
getMessage(): string | undefined;
|
|
1534
1580
|
};
|
|
1581
|
+
/** Skill capabilities — register and unregister standalone skills. */
|
|
1582
|
+
skills: {
|
|
1583
|
+
/** Register a Skill directory (containing SKILL.md) or a Skill object. Registering an existing name replaces it. */
|
|
1584
|
+
register(skill: SkillRegistration, scope?: ScopeRef): Promise<void>;
|
|
1585
|
+
/** Unregister a previously registered Skill by name. */
|
|
1586
|
+
unregister(skillName: string, scope?: ScopeRef): Promise<void> | void;
|
|
1587
|
+
};
|
|
1535
1588
|
/** Extension manifest from package.json `rowan` field. */
|
|
1536
1589
|
manifest?: ExtensionManifest;
|
|
1537
1590
|
/** Utility functions. */
|
|
@@ -1774,6 +1827,8 @@ interface BeforeToolCallEvent {
|
|
|
1774
1827
|
readonly agentId?: string;
|
|
1775
1828
|
readonly toolCallId?: string;
|
|
1776
1829
|
readonly metadata?: Readonly<Record<string, unknown>>;
|
|
1830
|
+
/** The invoking Agent's metadata, as the Tool's own call context carries it. */
|
|
1831
|
+
readonly agentMetadata?: Readonly<Record<string, unknown>>;
|
|
1777
1832
|
readonly answer?: unknown;
|
|
1778
1833
|
readonly scope?: ScopeRef;
|
|
1779
1834
|
readonly turn?: JsonObject;
|
|
@@ -3331,4 +3386,4 @@ declare function parseFrontmatter<T = Record<string, unknown>>(raw: string): Fro
|
|
|
3331
3386
|
|
|
3332
3387
|
declare function createCoreTools(input?: CoreToolContext): Tool$1[];
|
|
3333
3388
|
|
|
3334
|
-
export { type AfterToolCall, type AgentConfiguration, type AgentDefinition, type AgentId, type AgentListCursor, type AgentRecord, type AgentRun, AgentRuntime, type AgentRuntimeOptions, type AgentSummary, type AnyRuntimeError, type AssistantContent, type AssistantMessage, type BeforeToolCall, COMPACT_PHASE_ID, type ConfigProvider, type ConfigPutResult, type ConfigResolution, type ConfigToken, type ConfigurationSnapshot, type ContextCandidate, type ContextCompactionRecord, type ContextStatus, type CoreToolContext, DEFAULT_PHASE_ID, type DefinitionLayer, type DurableConsumer, type DurableRunEvent, type DurableStore, type DurableToolResult, type EntryPhaseSpec, type EventCursor, type EventId, type ExecutionCheckpoint, type ExecutionId, type ExecutionToken, type ExtensionAPI, type ExtensionActivationError, type ExtensionActivationResult, type ExtensionCapability, type ExtensionCapabilityContribution, type ExtensionContribution, type ExtensionDisposer, type ExtensionFactory, type ExtensionFactoryResult, type ExtensionHost, ExtensionLifetimeError, type ExtensionLifetimeErrorCode, type ExtensionLoadInput, type ExtensionStateStore, type ExtensionToolContribution, type FrontmatterResult, type HistorySeed, type HookEvent, type HookEventType, type HookHandler, type HostApiExtension, InMemoryConfigProvider, InMemoryExtensionHost, InMemoryStore, type InteractionRecord, type InvocationCatalogEntry, type InvocationSource, type JsonObject, type JsonPrimitive, type JsonValue, type LiveInteractionEvent, type LoadExtensionsResult, type LoadInput, type LoadResult, type LoadedExtension, type Message, type MessageBase, type MessageCommitted, type MessageContent, type MessageDelta, type MessageId, type MessageRevised, type MessageRevisionResult, type Metadata, type ModelRetry, type OpaqueId, type Outcome$1 as Outcome, type OwnerLease, type OwnerToken, type Page, type Phase, type PhaseContext, type PhaseContribution, type PhaseExecution, type PhaseExecutionIdentity, type PhaseInput, type PhaseInvocation, type PhaseMessageManager, type PhaseOutput, type PhaseRegistry, type PhaseRegistrySelection, type PhaseState, type PhaseStatus, type PhaseStatusState, type ResolvedResourceView, type ResourceDiagnostic, type ResourceKind, type ResourceRef, ResourceRegistry, ResourceRegistryError, type ResourceRegistryErrorCode, type ResourceSourceId, type ResourceView, type RetentionResult, type RunBoundary, type RunClaim, type RunEndEvent, type RunEvent, type RunFailure, type RunId, type RunInteraction, RunInteractionBoundary, RunInteractionCancelledError, type RunInteractionDriver, type RunInteractionKind, type RunInteractionRequest, type RunInteractionState, type RunInteractionStatus, type RunListCursor, type RunRecord, type RunSnapshot, type RunStartEvent, type RunState, type RunStateChanged, type RunSummary, RuntimeBootstrapRegistry, RuntimeError, type RuntimeErrorCode, type RuntimeErrorDetails, RuntimeExtensionLifetime, STOP_PHASE_ID, type SettingsBadge, type SettingsControl, type SettingsDefinition, type SettingsItem, type SettingsOption, type SettingsSection, type Skill, SqliteStore, type TextContent, type ThinkingContent, type ThinkingDelta, type Tool$1 as Tool, type ToolCallContext, type ToolCallDelta, type ToolCallId, type ToolCallPresentationInput, type ToolCallPresentationOutput, type ToolCallSnapshot, type ToolCallState, type ToolContribution, type ToolDefinition, type ToolExecutionResult, type ToolInvocationContext, type ToolMessage, type ToolMessageContent, type ToolResultContent, type ToolStateChanged, type ToolUseContent, type UserContent, type UserInput, type UserMessage, type WithdrawnUserInput, brandConfigToken, createCompactPhase, createCorePhases, createCoreTools, createDefaultPhase, createStopPhase, isConfigurationSnapshot, isRuntimeError, loadExtensionsFromPath as loadExtensions, loadPhase, loadPhases, loadSkill, loadSkills, mergeToolCall, parseAgentDefinition, parseFrontmatter, resolveConfigurationSnapshot };
|
|
3389
|
+
export { type AfterToolCall, type AgentConfiguration, type AgentDefinition, type AgentId, type AgentListCursor, type AgentRecord, type AgentRun, AgentRuntime, type AgentRuntimeOptions, type AgentSummary, type AnyRuntimeError, type AssistantContent, type AssistantMessage, type BeforeToolCall, COMPACT_PHASE_ID, type ConfigProvider, type ConfigPutResult, type ConfigResolution, type ConfigToken, type ConfigurationSnapshot, type ContextCandidate, type ContextCompactionRecord, type ContextStatus, type CoreToolContext, DEFAULT_PHASE_ID, type DefinitionLayer, type DurableConsumer, type DurableRunEvent, type DurableStore, type DurableToolResult, type EntryPhaseSpec, type EventCursor, type EventId, type ExecutionCheckpoint, type ExecutionId, type ExecutionToken, type ExtensionAPI, type ExtensionActivationError, type ExtensionActivationResult, type ExtensionCapability, type ExtensionCapabilityContribution, type ExtensionContribution, type ExtensionDisposer, type ExtensionFactory, type ExtensionFactoryResult, type ExtensionHost, ExtensionLifetimeError, type ExtensionLifetimeErrorCode, type ExtensionLoadInput, type ExtensionStateStore, type ExtensionToolContribution, type FrontmatterResult, type HistorySeed, type HookEvent, type HookEventType, type HookHandler, type HostApiExtension, InMemoryConfigProvider, InMemoryExtensionHost, InMemoryStore, type InteractionRecord, type InvocationCatalogEntry, type InvocationSource, type JsonObject, type JsonPrimitive, type JsonValue, type LiveInteractionEvent, type LoadExtensionsResult, type LoadInput, type LoadResult, type LoadedExtension, type Message, type MessageBase, type MessageCommitted, type MessageContent, type MessageDelta, type MessageId, type MessageRevised, type MessageRevisionResult, type Metadata, type ModelRetry, type OpaqueId, type Outcome$1 as Outcome, type OwnerLease, type OwnerToken, type Page, type Phase, type PhaseContext, type PhaseContribution, type PhaseExecution, type PhaseExecutionIdentity, type PhaseInput, type PhaseInvocation, type PhaseMessageManager, type PhaseOutput, type PhaseRegistry, type PhaseRegistrySelection, type PhaseState, type PhaseStatus, type PhaseStatusState, type ResolvedResourceView, type ResourceDiagnostic, type ResourceKind, type ResourceRef, ResourceRegistry, ResourceRegistryError, type ResourceRegistryErrorCode, type ResourceSourceId, type ResourceView, type RetentionResult, type RunBoundary, type RunClaim, type RunEndEvent, type RunEvent, type RunFailure, type RunId, type RunInteraction, RunInteractionBoundary, RunInteractionCancelledError, type RunInteractionDriver, type RunInteractionKind, type RunInteractionRequest, type RunInteractionState, type RunInteractionStatus, type RunListCursor, type RunRecord, type RunSnapshot, type RunStartEvent, type RunState, type RunStateChanged, type RunSummary, RuntimeBootstrapRegistry, RuntimeError, type RuntimeErrorCode, type RuntimeErrorDetails, RuntimeExtensionLifetime, STOP_PHASE_ID, type SettingsBadge, type SettingsControl, type SettingsDefinition, type SettingsItem, type SettingsOption, type SettingsSection, type Skill, type SkillRegistration, SqliteStore, type TextContent, type ThinkingContent, type ThinkingDelta, type Tool$1 as Tool, type ToolCallContext, type ToolCallDelta, type ToolCallId, type ToolCallPresentationInput, type ToolCallPresentationOutput, type ToolCallSnapshot, type ToolCallState, type ToolContribution, type ToolDefinition, type ToolExecutionResult, type ToolInvocationContext, type ToolMessage, type ToolMessageContent, type ToolResultContent, type ToolStateChanged, type ToolUseContent, type UserContent, type UserInput, type UserMessage, type WithdrawnUserInput, brandConfigToken, createCompactPhase, createCorePhases, createCoreTools, createDefaultPhase, createStopPhase, extensionSourceId, isConfigurationSnapshot, isRuntimeError, loadExtensionsFromPath as loadExtensions, loadPhase, loadPhases, loadSkill, loadSkills, mergeToolCall, parseAgentDefinition, parseFrontmatter, resolveConfigurationSnapshot };
|
package/dist/index.js
CHANGED
|
@@ -1702,13 +1702,13 @@ function createExtensionAPI(hooks, options, runtime, eventBus) {
|
|
|
1702
1702
|
}
|
|
1703
1703
|
},
|
|
1704
1704
|
tools: {
|
|
1705
|
-
register: (tool) => {
|
|
1705
|
+
register: (tool, scope) => {
|
|
1706
1706
|
assertActive();
|
|
1707
|
-
options?.registerTool?.(tool);
|
|
1707
|
+
return Promise.resolve(options?.registerTool?.(tool, scope));
|
|
1708
1708
|
},
|
|
1709
|
-
unregister: (toolName) => {
|
|
1709
|
+
unregister: (toolName, scope) => {
|
|
1710
1710
|
assertActive();
|
|
1711
|
-
options?.unregisterTool?.(toolName);
|
|
1711
|
+
return Promise.resolve(options?.unregisterTool?.(toolName, scope));
|
|
1712
1712
|
}
|
|
1713
1713
|
},
|
|
1714
1714
|
capabilities: {
|
|
@@ -1762,13 +1762,13 @@ function createExtensionAPI(hooks, options, runtime, eventBus) {
|
|
|
1762
1762
|
}, emit: () => {
|
|
1763
1763
|
}, has: () => false, count: () => 0 },
|
|
1764
1764
|
phases: {
|
|
1765
|
-
register: async (registration) => {
|
|
1765
|
+
register: async (registration, scope) => {
|
|
1766
1766
|
assertActive();
|
|
1767
|
-
await options?.registerPhase?.(registration);
|
|
1767
|
+
await options?.registerPhase?.(registration, scope);
|
|
1768
1768
|
},
|
|
1769
|
-
unregister: (phaseName) => {
|
|
1769
|
+
unregister: (phaseName, scope) => {
|
|
1770
1770
|
assertActive();
|
|
1771
|
-
options?.unregisterPhase?.(phaseName);
|
|
1771
|
+
return options?.unregisterPhase?.(phaseName, scope);
|
|
1772
1772
|
},
|
|
1773
1773
|
getPayload: () => outputPayload,
|
|
1774
1774
|
setPayload: (p) => {
|
|
@@ -1783,6 +1783,16 @@ function createExtensionAPI(hooks, options, runtime, eventBus) {
|
|
|
1783
1783
|
},
|
|
1784
1784
|
getNextPhase: () => nextPhase,
|
|
1785
1785
|
getMessage: () => outputMessage
|
|
1786
|
+
},
|
|
1787
|
+
skills: {
|
|
1788
|
+
register: async (skill, scope) => {
|
|
1789
|
+
assertActive();
|
|
1790
|
+
await options?.registerSkill?.(skill, scope);
|
|
1791
|
+
},
|
|
1792
|
+
unregister: (skillName, scope) => {
|
|
1793
|
+
assertActive();
|
|
1794
|
+
return options?.unregisterSkill?.(skillName, scope);
|
|
1795
|
+
}
|
|
1786
1796
|
}
|
|
1787
1797
|
};
|
|
1788
1798
|
if (options?.namespaces) {
|
|
@@ -3573,6 +3583,12 @@ async function executePhase(ctx) {
|
|
|
3573
3583
|
const api = createExtensionAPI(void 0, {
|
|
3574
3584
|
registerPhase: async () => {
|
|
3575
3585
|
},
|
|
3586
|
+
unregisterPhase: () => {
|
|
3587
|
+
},
|
|
3588
|
+
registerSkill: async () => {
|
|
3589
|
+
},
|
|
3590
|
+
unregisterSkill: () => {
|
|
3591
|
+
},
|
|
3576
3592
|
registerProvider: () => {
|
|
3577
3593
|
},
|
|
3578
3594
|
unregisterProvider: () => {
|
|
@@ -5171,6 +5187,7 @@ function assembleRegisteredExtensions(snapshot, runner, options = {}) {
|
|
|
5171
5187
|
agentId: input.context.agentId,
|
|
5172
5188
|
toolCallId: input.context.toolCallId,
|
|
5173
5189
|
metadata: input.context.runMetadata,
|
|
5190
|
+
...input.context.agentMetadata === void 0 ? {} : { agentMetadata: input.context.agentMetadata },
|
|
5174
5191
|
answer: input.answer,
|
|
5175
5192
|
scope: input.context.scope,
|
|
5176
5193
|
turn: input.context.turn
|
|
@@ -6023,6 +6040,10 @@ function createEventBus() {
|
|
|
6023
6040
|
}
|
|
6024
6041
|
|
|
6025
6042
|
// src/extensions/runner.ts
|
|
6043
|
+
function extensionSourceId(scope) {
|
|
6044
|
+
if (!scope || scope.length === 0) return "rowan.extensions";
|
|
6045
|
+
return `rowan.extensions:${scopeToKey(scope)}`;
|
|
6046
|
+
}
|
|
6026
6047
|
async function execCommand(command, args, cwd, options) {
|
|
6027
6048
|
return new Promise((resolve9, reject) => {
|
|
6028
6049
|
const child = execFile(
|
|
@@ -6105,6 +6126,8 @@ var ExtensionRunner = class {
|
|
|
6105
6126
|
// Phase management
|
|
6106
6127
|
phases = /* @__PURE__ */ new Map();
|
|
6107
6128
|
_phaseCache = null;
|
|
6129
|
+
// Skill management
|
|
6130
|
+
skills = /* @__PURE__ */ new Map();
|
|
6108
6131
|
// Provider management
|
|
6109
6132
|
pendingProviders = [];
|
|
6110
6133
|
bound = false;
|
|
@@ -6112,6 +6135,8 @@ var ExtensionRunner = class {
|
|
|
6112
6135
|
errorListeners = /* @__PURE__ */ new Set();
|
|
6113
6136
|
// Capability change listeners
|
|
6114
6137
|
capabilityListeners = /* @__PURE__ */ new Set();
|
|
6138
|
+
// Resource change listeners (for Registry live sync)
|
|
6139
|
+
resourceChangeListeners = /* @__PURE__ */ new Set();
|
|
6115
6140
|
/** Current agent context — set by the agent before each phase */
|
|
6116
6141
|
currentContext;
|
|
6117
6142
|
constructor(options) {
|
|
@@ -6122,7 +6147,7 @@ var ExtensionRunner = class {
|
|
|
6122
6147
|
this.host = options?.host ?? new InMemoryExtensionHost();
|
|
6123
6148
|
if (this.host.onConfigChanged) {
|
|
6124
6149
|
const unsub = this.host.onConfigChanged((extensionId, scope) => {
|
|
6125
|
-
this.notifyConfigChanged(extensionId, scope);
|
|
6150
|
+
void this.notifyConfigChanged(extensionId, scope);
|
|
6126
6151
|
});
|
|
6127
6152
|
if (typeof unsub === "function") {
|
|
6128
6153
|
this.hostUnsubscribers.push(unsub);
|
|
@@ -6215,6 +6240,7 @@ var ExtensionRunner = class {
|
|
|
6215
6240
|
path: ext.path,
|
|
6216
6241
|
tools: /* @__PURE__ */ new Map(),
|
|
6217
6242
|
phases: /* @__PURE__ */ new Set(),
|
|
6243
|
+
skills: /* @__PURE__ */ new Set(),
|
|
6218
6244
|
capabilities: /* @__PURE__ */ new Map(),
|
|
6219
6245
|
cleanup: [],
|
|
6220
6246
|
runtime: createExtensionRuntime(),
|
|
@@ -6259,19 +6285,22 @@ var ExtensionRunner = class {
|
|
|
6259
6285
|
}
|
|
6260
6286
|
this.extensions.length = 0;
|
|
6261
6287
|
this.capabilityListeners.clear();
|
|
6288
|
+
this.resourceChangeListeners.clear();
|
|
6262
6289
|
this.phases.clear();
|
|
6263
6290
|
this._phaseCache = null;
|
|
6291
|
+
this.skills.clear();
|
|
6292
|
+
this.bound = false;
|
|
6264
6293
|
this.runtime.invalidate("This Extension Runtime has been closed.");
|
|
6265
6294
|
}
|
|
6266
6295
|
get extensionHost() {
|
|
6267
6296
|
return this.host;
|
|
6268
6297
|
}
|
|
6269
|
-
notifyConfigChanged(extensionId, scope) {
|
|
6298
|
+
async notifyConfigChanged(extensionId, scope) {
|
|
6270
6299
|
const listeners = this.configChangeListeners.get(extensionId);
|
|
6271
6300
|
if (!listeners) return;
|
|
6272
6301
|
for (const listener of listeners) {
|
|
6273
6302
|
try {
|
|
6274
|
-
listener(scope);
|
|
6303
|
+
await listener(scope);
|
|
6275
6304
|
} catch (error) {
|
|
6276
6305
|
this.emitError({
|
|
6277
6306
|
extensionPath: "<runtime>",
|
|
@@ -6326,8 +6355,9 @@ var ExtensionRunner = class {
|
|
|
6326
6355
|
*/
|
|
6327
6356
|
getToolDefinition(toolName) {
|
|
6328
6357
|
for (const ext of this.extensions) {
|
|
6329
|
-
const tool
|
|
6330
|
-
|
|
6358
|
+
for (const tool of ext.tools.values()) {
|
|
6359
|
+
if (tool.definition.name === toolName) return tool.definition;
|
|
6360
|
+
}
|
|
6331
6361
|
}
|
|
6332
6362
|
return void 0;
|
|
6333
6363
|
}
|
|
@@ -6357,6 +6387,20 @@ var ExtensionRunner = class {
|
|
|
6357
6387
|
this.capabilityListeners.add(listener);
|
|
6358
6388
|
return () => this.capabilityListeners.delete(listener);
|
|
6359
6389
|
}
|
|
6390
|
+
/**
|
|
6391
|
+
* Subscribe to resource changes (tools, phases, skills registered, unregistered, or disposed).
|
|
6392
|
+
* Used by RuntimeBootstrapRegistry to re-commit implicit sources after activation.
|
|
6393
|
+
*/
|
|
6394
|
+
onResourceChange(listener) {
|
|
6395
|
+
this.resourceChangeListeners.add(listener);
|
|
6396
|
+
return () => this.resourceChangeListeners.delete(listener);
|
|
6397
|
+
}
|
|
6398
|
+
async notifyResourceChange(kind) {
|
|
6399
|
+
if (!this.bound) return;
|
|
6400
|
+
for (const listener of this.resourceChangeListeners) {
|
|
6401
|
+
await listener(kind);
|
|
6402
|
+
}
|
|
6403
|
+
}
|
|
6360
6404
|
triggerUiAction(event) {
|
|
6361
6405
|
this.events.emit("ui.action", event);
|
|
6362
6406
|
}
|
|
@@ -6364,20 +6408,24 @@ var ExtensionRunner = class {
|
|
|
6364
6408
|
// Phase management
|
|
6365
6409
|
// ---------------------------------------------------------------------------
|
|
6366
6410
|
getPhase(name) {
|
|
6367
|
-
const reg
|
|
6368
|
-
|
|
6369
|
-
|
|
6411
|
+
for (const reg of this.collectRegisteredPhases().values()) {
|
|
6412
|
+
if (reg.definition.name === name) return this.adaptToPhase(reg);
|
|
6413
|
+
}
|
|
6414
|
+
return void 0;
|
|
6370
6415
|
}
|
|
6371
6416
|
getPhases() {
|
|
6372
6417
|
return [...this.collectRegisteredPhases().values()].map(
|
|
6373
6418
|
(p) => this.adaptToPhase(p)
|
|
6374
6419
|
);
|
|
6375
6420
|
}
|
|
6421
|
+
getRegisteredPhases() {
|
|
6422
|
+
return [...this.collectRegisteredPhases().values()];
|
|
6423
|
+
}
|
|
6376
6424
|
createPhaseRegistry(input = {}) {
|
|
6377
6425
|
const registered = this.collectRegisteredPhases();
|
|
6378
6426
|
const phases = /* @__PURE__ */ new Map();
|
|
6379
|
-
for (const
|
|
6380
|
-
phases.set(name, this.adaptToPhase(reg));
|
|
6427
|
+
for (const reg of registered.values()) {
|
|
6428
|
+
phases.set(reg.definition.name, this.adaptToPhase(reg));
|
|
6381
6429
|
}
|
|
6382
6430
|
const entryPhaseId = input.entryPhaseId ?? null;
|
|
6383
6431
|
return { phases, entryPhaseId };
|
|
@@ -6393,6 +6441,15 @@ var ExtensionRunner = class {
|
|
|
6393
6441
|
};
|
|
6394
6442
|
}
|
|
6395
6443
|
// ---------------------------------------------------------------------------
|
|
6444
|
+
// Skill management
|
|
6445
|
+
// ---------------------------------------------------------------------------
|
|
6446
|
+
getSkills() {
|
|
6447
|
+
return [...this.skills.values()].map((s) => s.definition);
|
|
6448
|
+
}
|
|
6449
|
+
getRegisteredSkills() {
|
|
6450
|
+
return [...this.skills.values()];
|
|
6451
|
+
}
|
|
6452
|
+
// ---------------------------------------------------------------------------
|
|
6396
6453
|
// Lifecycle
|
|
6397
6454
|
// ---------------------------------------------------------------------------
|
|
6398
6455
|
/**
|
|
@@ -6487,6 +6544,7 @@ var ExtensionRunner = class {
|
|
|
6487
6544
|
...context?.agentId !== void 0 ? { agentId: context.agentId } : {},
|
|
6488
6545
|
...context?.toolCallId !== void 0 ? { toolCallId: context.toolCallId } : {},
|
|
6489
6546
|
...context?.metadata !== void 0 ? { metadata: context.metadata } : {},
|
|
6547
|
+
...context?.agentMetadata !== void 0 ? { agentMetadata: context.agentMetadata } : {},
|
|
6490
6548
|
...context?.answer !== void 0 ? { answer: context.answer } : {},
|
|
6491
6549
|
scope,
|
|
6492
6550
|
turn
|
|
@@ -6567,12 +6625,14 @@ var ExtensionRunner = class {
|
|
|
6567
6625
|
}
|
|
6568
6626
|
};
|
|
6569
6627
|
return createExtensionAPI(this.hooks, {
|
|
6570
|
-
registerPhase: (registration) => this.registerPhase(extension, registration),
|
|
6571
|
-
unregisterPhase: (phaseName) => this.unregisterPhase(extension, phaseName),
|
|
6628
|
+
registerPhase: (registration, scope) => this.registerPhase(extension, registration, scope),
|
|
6629
|
+
unregisterPhase: (phaseName, scope) => this.unregisterPhase(extension, phaseName, scope),
|
|
6630
|
+
registerSkill: (registration, scope) => this.registerSkill(extension, registration, scope),
|
|
6631
|
+
unregisterSkill: (skillName, scope) => this.unregisterSkill(extension, skillName, scope),
|
|
6572
6632
|
registerProvider: (config) => this.registerProvider(config),
|
|
6573
6633
|
unregisterProvider: (name) => this.unregisterProvider(name),
|
|
6574
|
-
registerTool: (tool) => this.registerTool(extension, tool),
|
|
6575
|
-
unregisterTool: (toolName) => this.unregisterTool(extension, toolName),
|
|
6634
|
+
registerTool: (tool, scope) => this.registerTool(extension, tool, scope),
|
|
6635
|
+
unregisterTool: (toolName, scope) => this.unregisterTool(extension, toolName, scope),
|
|
6576
6636
|
contributeCapability: (contribution) => this.contributeCapability(extension, contribution),
|
|
6577
6637
|
context: extContext,
|
|
6578
6638
|
manifest,
|
|
@@ -6618,12 +6678,16 @@ var ExtensionRunner = class {
|
|
|
6618
6678
|
}
|
|
6619
6679
|
}, extension.runtime, this.events);
|
|
6620
6680
|
}
|
|
6621
|
-
|
|
6622
|
-
|
|
6681
|
+
// Validation stays synchronous so a duplicate throws at the call site even
|
|
6682
|
+
// when the caller does not await the Registry re-commit.
|
|
6683
|
+
registerTool(extension, tool, scope) {
|
|
6684
|
+
const sourceId = extensionSourceId(scope);
|
|
6685
|
+
const regKey = `${sourceId}::${tool.name}`;
|
|
6686
|
+
if (extension.tools.has(regKey)) {
|
|
6623
6687
|
throw new Error(`Duplicate Tool name "${tool.name}" in extension ${extension.path}.`);
|
|
6624
6688
|
}
|
|
6625
6689
|
for (const ext of this.extensions) {
|
|
6626
|
-
if (ext.tools.has(
|
|
6690
|
+
if (ext.tools.has(regKey)) {
|
|
6627
6691
|
const message = `Duplicate Tool name "${tool.name}" from extensions ${ext.path} and ${extension.path}.`;
|
|
6628
6692
|
this.emitError({
|
|
6629
6693
|
extensionPath: extension.path,
|
|
@@ -6634,15 +6698,19 @@ var ExtensionRunner = class {
|
|
|
6634
6698
|
}
|
|
6635
6699
|
}
|
|
6636
6700
|
const sourceInfo = createSourceInfo(extension.path);
|
|
6637
|
-
extension.tools.set(
|
|
6701
|
+
extension.tools.set(regKey, {
|
|
6638
6702
|
definition: tool,
|
|
6639
|
-
sourceInfo
|
|
6703
|
+
sourceInfo,
|
|
6704
|
+
sourceId,
|
|
6705
|
+
scope
|
|
6640
6706
|
});
|
|
6707
|
+
return this.notifyResourceChange("tool");
|
|
6641
6708
|
}
|
|
6642
|
-
unregisterTool(extension, toolName) {
|
|
6643
|
-
|
|
6644
|
-
|
|
6645
|
-
|
|
6709
|
+
unregisterTool(extension, toolName, scope) {
|
|
6710
|
+
const sourceId = extensionSourceId(scope);
|
|
6711
|
+
const regKey = `${sourceId}::${toolName}`;
|
|
6712
|
+
if (!extension.tools.delete(regKey)) return Promise.resolve();
|
|
6713
|
+
return this.notifyResourceChange("tool");
|
|
6646
6714
|
}
|
|
6647
6715
|
contributeCapability(extension, contribution) {
|
|
6648
6716
|
const key = `${contribution.kind}:${contribution.name}`;
|
|
@@ -6684,53 +6752,101 @@ var ExtensionRunner = class {
|
|
|
6684
6752
|
}
|
|
6685
6753
|
}
|
|
6686
6754
|
}
|
|
6687
|
-
async registerPhase(extension, registration) {
|
|
6755
|
+
async registerPhase(extension, registration, scope) {
|
|
6688
6756
|
if (typeof registration === "string") {
|
|
6689
6757
|
if (registration.length === 0) {
|
|
6690
6758
|
throw new Error(`Phase registration requires a directory path.`);
|
|
6691
6759
|
}
|
|
6692
|
-
return this.loadRegisteredPhase(extension, registration);
|
|
6760
|
+
return this.loadRegisteredPhase(extension, registration, scope);
|
|
6693
6761
|
}
|
|
6694
6762
|
if (typeof registration === "object" && registration !== null && "name" in registration) {
|
|
6695
|
-
return this.registerPhaseDefinition(extension, registration);
|
|
6763
|
+
return this.registerPhaseDefinition(extension, registration, scope);
|
|
6696
6764
|
}
|
|
6697
6765
|
throw new Error(`Phase registration requires a directory path or Phase object.`);
|
|
6698
6766
|
}
|
|
6699
|
-
registerPhaseDefinition(extension, phase) {
|
|
6767
|
+
async registerPhaseDefinition(extension, phase, scope) {
|
|
6768
|
+
const sourceId = extensionSourceId(scope);
|
|
6700
6769
|
const name = phase.name;
|
|
6701
|
-
|
|
6770
|
+
const regKey = `${sourceId}::${name}`;
|
|
6771
|
+
if (this.phases.has(regKey)) {
|
|
6702
6772
|
throw new Error(`Duplicate phase name: ${name}`);
|
|
6703
6773
|
}
|
|
6704
6774
|
const registered = {
|
|
6705
6775
|
definition: phase,
|
|
6706
|
-
source: { extensionPath: extension.path }
|
|
6776
|
+
source: { extensionPath: extension.path },
|
|
6777
|
+
sourceId,
|
|
6778
|
+
scope
|
|
6707
6779
|
};
|
|
6708
|
-
this.phases.set(
|
|
6709
|
-
extension.phases.add(
|
|
6780
|
+
this.phases.set(regKey, registered);
|
|
6781
|
+
extension.phases.add(regKey);
|
|
6710
6782
|
this._phaseCache = null;
|
|
6783
|
+
await this.notifyResourceChange("phase");
|
|
6711
6784
|
}
|
|
6712
|
-
unregisterPhase(extension, phaseName) {
|
|
6713
|
-
const
|
|
6785
|
+
async unregisterPhase(extension, phaseName, scope) {
|
|
6786
|
+
const sourceId = extensionSourceId(scope);
|
|
6787
|
+
const regKey = `${sourceId}::${phaseName}`;
|
|
6788
|
+
const registered = this.phases.get(regKey);
|
|
6714
6789
|
if (registered && registered.source.extensionPath === extension.path) {
|
|
6715
|
-
this.phases.delete(
|
|
6716
|
-
extension.phases.delete(
|
|
6790
|
+
this.phases.delete(regKey);
|
|
6791
|
+
extension.phases.delete(regKey);
|
|
6717
6792
|
this._phaseCache = null;
|
|
6793
|
+
await this.notifyResourceChange("phase");
|
|
6718
6794
|
}
|
|
6719
6795
|
}
|
|
6720
|
-
async loadRegisteredPhase(extension, registration) {
|
|
6796
|
+
async loadRegisteredPhase(extension, registration, scope) {
|
|
6721
6797
|
const extensionBase = extension.path.startsWith("<") ? this.cwd : dirname6(extension.path);
|
|
6722
6798
|
const phase = await loadPhase(resolve5(extensionBase, registration));
|
|
6723
|
-
|
|
6724
|
-
|
|
6725
|
-
|
|
6799
|
+
await this.registerPhaseDefinition(extension, phase, scope);
|
|
6800
|
+
}
|
|
6801
|
+
async registerSkill(extension, registration, scope) {
|
|
6802
|
+
if (typeof registration === "string") {
|
|
6803
|
+
if (registration.length === 0) {
|
|
6804
|
+
throw new Error(`Skill registration requires a directory path.`);
|
|
6805
|
+
}
|
|
6806
|
+
return this.loadRegisteredSkill(extension, registration, scope);
|
|
6807
|
+
}
|
|
6808
|
+
if (typeof registration === "object" && registration !== null && "name" in registration) {
|
|
6809
|
+
return this.registerSkillDefinition(extension, registration, scope);
|
|
6810
|
+
}
|
|
6811
|
+
throw new Error(`Skill registration requires a directory path or Skill object.`);
|
|
6812
|
+
}
|
|
6813
|
+
async registerSkillDefinition(extension, skill, scope) {
|
|
6814
|
+
const sourceId = extensionSourceId(scope);
|
|
6815
|
+
const name = skill.name;
|
|
6816
|
+
const regKey = `${sourceId}::${name}`;
|
|
6817
|
+
const existing = this.skills.get(regKey);
|
|
6818
|
+
if (existing && existing.source.extensionPath !== extension.path) {
|
|
6819
|
+
for (const ext of this.extensions) {
|
|
6820
|
+
if (ext.path === existing.source.extensionPath) {
|
|
6821
|
+
ext.skills.delete(regKey);
|
|
6822
|
+
break;
|
|
6823
|
+
}
|
|
6824
|
+
}
|
|
6726
6825
|
}
|
|
6727
6826
|
const registered = {
|
|
6728
|
-
definition:
|
|
6729
|
-
source: { extensionPath: extension.path }
|
|
6827
|
+
definition: skill,
|
|
6828
|
+
source: { extensionPath: extension.path },
|
|
6829
|
+
sourceId,
|
|
6830
|
+
scope
|
|
6730
6831
|
};
|
|
6731
|
-
this.
|
|
6732
|
-
extension.
|
|
6733
|
-
this.
|
|
6832
|
+
this.skills.set(regKey, registered);
|
|
6833
|
+
extension.skills.add(regKey);
|
|
6834
|
+
await this.notifyResourceChange("skill");
|
|
6835
|
+
}
|
|
6836
|
+
async unregisterSkill(extension, skillName, scope) {
|
|
6837
|
+
const sourceId = extensionSourceId(scope);
|
|
6838
|
+
const regKey = `${sourceId}::${skillName}`;
|
|
6839
|
+
const registered = this.skills.get(regKey);
|
|
6840
|
+
if (registered && registered.source.extensionPath === extension.path) {
|
|
6841
|
+
this.skills.delete(regKey);
|
|
6842
|
+
extension.skills.delete(regKey);
|
|
6843
|
+
await this.notifyResourceChange("skill");
|
|
6844
|
+
}
|
|
6845
|
+
}
|
|
6846
|
+
async loadRegisteredSkill(extension, registration, scope) {
|
|
6847
|
+
const extensionBase = extension.path.startsWith("<") ? this.cwd : dirname6(extension.path);
|
|
6848
|
+
const skill = await loadSkill(resolve5(extensionBase, registration));
|
|
6849
|
+
await this.registerSkillDefinition(extension, skill, scope);
|
|
6734
6850
|
}
|
|
6735
6851
|
registerProvider(config) {
|
|
6736
6852
|
if (this.bound) {
|
|
@@ -6769,7 +6885,18 @@ var ExtensionRunner = class {
|
|
|
6769
6885
|
}
|
|
6770
6886
|
async disposeExtension(extension, message) {
|
|
6771
6887
|
extension.runtime.invalidate(message);
|
|
6888
|
+
const hadTools = extension.tools.size > 0;
|
|
6889
|
+
const hadPhases = extension.phases.size > 0;
|
|
6890
|
+
const hadSkills = extension.skills.size > 0;
|
|
6891
|
+
extension.tools.clear();
|
|
6772
6892
|
for (const name of extension.phases) this.phases.delete(name);
|
|
6893
|
+
extension.phases.clear();
|
|
6894
|
+
for (const name of extension.skills) {
|
|
6895
|
+
if (this.skills.get(name)?.source.extensionPath === extension.path) {
|
|
6896
|
+
this.skills.delete(name);
|
|
6897
|
+
}
|
|
6898
|
+
}
|
|
6899
|
+
extension.skills.clear();
|
|
6773
6900
|
const hadCapabilities = extension.capabilities.size > 0;
|
|
6774
6901
|
extension.capabilities.clear();
|
|
6775
6902
|
for (const cleanup of [...extension.cleanup].reverse()) {
|
|
@@ -6787,6 +6914,11 @@ var ExtensionRunner = class {
|
|
|
6787
6914
|
if (hadCapabilities) {
|
|
6788
6915
|
this.notifyCapabilitiesChanged();
|
|
6789
6916
|
}
|
|
6917
|
+
if (this.bound) {
|
|
6918
|
+
if (hadTools) await this.notifyResourceChange("tool");
|
|
6919
|
+
if (hadPhases) await this.notifyResourceChange("phase");
|
|
6920
|
+
if (hadSkills) await this.notifyResourceChange("skill");
|
|
6921
|
+
}
|
|
6790
6922
|
}
|
|
6791
6923
|
};
|
|
6792
6924
|
function createExtensionRunner(options) {
|
|
@@ -6963,7 +7095,7 @@ var ResourceRegistryError = class extends Error {
|
|
|
6963
7095
|
}
|
|
6964
7096
|
};
|
|
6965
7097
|
var RESOURCE_NAME = /^[A-Za-z0-9][A-Za-z0-9._:-]*$/;
|
|
6966
|
-
var SOURCE_ID = /^[A-Za-z0-9][A-Za-z0-9._
|
|
7098
|
+
var SOURCE_ID = /^[A-Za-z0-9][A-Za-z0-9._:/-]*$/;
|
|
6967
7099
|
var ResourceRegistry = class {
|
|
6968
7100
|
sources = /* @__PURE__ */ new Map();
|
|
6969
7101
|
/** Sources registered by the bootstrap boundary (currently Extensions). */
|
|
@@ -7056,15 +7188,7 @@ var ResourceRegistry = class {
|
|
|
7056
7188
|
}
|
|
7057
7189
|
withImplicit(kind, sourceIds) {
|
|
7058
7190
|
const combined = [...sourceIds];
|
|
7059
|
-
|
|
7060
|
-
for (const sourceId of this.implicitSources.get(kind) ?? []) {
|
|
7061
|
-
if (sourceId === "rowan.core") {
|
|
7062
|
-
hasCore = true;
|
|
7063
|
-
} else if (!combined.includes(sourceId)) {
|
|
7064
|
-
combined.push(sourceId);
|
|
7065
|
-
}
|
|
7066
|
-
}
|
|
7067
|
-
if (hasCore && !combined.includes("rowan.core")) {
|
|
7191
|
+
if (this.hasImplicit(kind, "rowan.core") && !combined.includes("rowan.core")) {
|
|
7068
7192
|
combined.push("rowan.core");
|
|
7069
7193
|
}
|
|
7070
7194
|
return combined;
|
|
@@ -7139,9 +7263,6 @@ var ResourceRegistry = class {
|
|
|
7139
7263
|
if (source.sourceId === "rowan.core") {
|
|
7140
7264
|
continue;
|
|
7141
7265
|
}
|
|
7142
|
-
if (source.sourceId === "rowan.extensions" && isCoreResourceName(kind, value.name)) {
|
|
7143
|
-
continue;
|
|
7144
|
-
}
|
|
7145
7266
|
throw new ResourceRegistryError(
|
|
7146
7267
|
"resource_collision",
|
|
7147
7268
|
`Duplicate ${capitalize(kind)} resource "${value.name}" in Resource View.`
|
|
@@ -7165,9 +7286,6 @@ var ResourceRegistry = class {
|
|
|
7165
7286
|
if (source.sourceId === "rowan.core") {
|
|
7166
7287
|
continue;
|
|
7167
7288
|
}
|
|
7168
|
-
if (source.sourceId === "rowan.extensions" && isCoreResourceName(kind, value.name)) {
|
|
7169
|
-
continue;
|
|
7170
|
-
}
|
|
7171
7289
|
throw new ResourceRegistryError("resource_collision", `Duplicate ${capitalize(kind)} resource "${value.name}" in Resource View.`);
|
|
7172
7290
|
}
|
|
7173
7291
|
seenNames.add(value.name);
|
|
@@ -7186,10 +7304,7 @@ var ResourceRegistry = class {
|
|
|
7186
7304
|
seen.add(sourceId);
|
|
7187
7305
|
const source = bySource?.get(sourceId);
|
|
7188
7306
|
if (!source) {
|
|
7189
|
-
|
|
7190
|
-
"unknown_resource_source",
|
|
7191
|
-
`Unknown resource source "${sourceId}" for ${kind}.`
|
|
7192
|
-
);
|
|
7307
|
+
continue;
|
|
7193
7308
|
}
|
|
7194
7309
|
sources.push(source);
|
|
7195
7310
|
}
|
|
@@ -7241,9 +7356,6 @@ function capitalize(value) {
|
|
|
7241
7356
|
function isImplicitCoreName(kind, name) {
|
|
7242
7357
|
return kind === "tool" && name === "route";
|
|
7243
7358
|
}
|
|
7244
|
-
function isCoreResourceName(kind, name) {
|
|
7245
|
-
return kind === "tool" && CORE_TOOL_NAMES.has(name) || kind === "phase" && CORE_PHASE_NAMES.has(name);
|
|
7246
|
-
}
|
|
7247
7359
|
async function loadDirectoryValues(kind, directory, sourceId) {
|
|
7248
7360
|
const root = resolve7(directory);
|
|
7249
7361
|
let rootInfo;
|
|
@@ -7407,12 +7519,24 @@ var RuntimeExtensionLifetime = class {
|
|
|
7407
7519
|
phases() {
|
|
7408
7520
|
return this.runner.getPhases();
|
|
7409
7521
|
}
|
|
7522
|
+
registeredPhases() {
|
|
7523
|
+
return this.runner.getRegisteredPhases();
|
|
7524
|
+
}
|
|
7525
|
+
skills() {
|
|
7526
|
+
return this.runner.getSkills();
|
|
7527
|
+
}
|
|
7528
|
+
registeredSkills() {
|
|
7529
|
+
return this.runner.getRegisteredSkills();
|
|
7530
|
+
}
|
|
7410
7531
|
get extensionRunner() {
|
|
7411
7532
|
return this.runner;
|
|
7412
7533
|
}
|
|
7413
7534
|
get extensionHost() {
|
|
7414
7535
|
return this.runner.extensionHost;
|
|
7415
7536
|
}
|
|
7537
|
+
onResourceChange(listener) {
|
|
7538
|
+
return this.runner.onResourceChange(listener);
|
|
7539
|
+
}
|
|
7416
7540
|
dropRunState(runId) {
|
|
7417
7541
|
this.runner.dropRunState(runId);
|
|
7418
7542
|
}
|
|
@@ -7426,9 +7550,33 @@ var RuntimeBootstrapRegistry = class extends ResourceRegistry {
|
|
|
7426
7550
|
constructor(extensions = new RuntimeExtensionLifetime()) {
|
|
7427
7551
|
super();
|
|
7428
7552
|
this.extensions = extensions;
|
|
7553
|
+
this.extensions.onResourceChange((kind) => this.recommit(kind));
|
|
7429
7554
|
}
|
|
7430
7555
|
extensions;
|
|
7431
|
-
|
|
7556
|
+
knownSources = /* @__PURE__ */ new Map();
|
|
7557
|
+
commitQueue = Promise.resolve();
|
|
7558
|
+
recommit(kind) {
|
|
7559
|
+
const next = this.commitQueue.then(async () => {
|
|
7560
|
+
const entries = kind === "tool" ? this.extensions.tools().map((tool) => [tool.sourceId, adaptExtensionTool(tool)]) : kind === "phase" ? this.extensions.registeredPhases().map((reg) => [reg.sourceId, this.extensions.extensionRunner.adaptToPhase(reg)]) : this.extensions.registeredSkills().map((reg) => [reg.sourceId, reg.definition]);
|
|
7561
|
+
const bySource = /* @__PURE__ */ new Map();
|
|
7562
|
+
for (const [sourceId, value] of entries) bySource.set(sourceId, [...bySource.get(sourceId) ?? [], value]);
|
|
7563
|
+
const known = this.knownSources.get(kind) ?? /* @__PURE__ */ new Set();
|
|
7564
|
+
this.knownSources.set(kind, known);
|
|
7565
|
+
for (const [sourceId, values] of bySource) {
|
|
7566
|
+
known.add(sourceId);
|
|
7567
|
+
if (kind === "tool") await this.loadTools({ sourceId, values });
|
|
7568
|
+
else if (kind === "phase") await this.loadPhases({ sourceId, values });
|
|
7569
|
+
else await this.loadSkills({ sourceId, values });
|
|
7570
|
+
}
|
|
7571
|
+
for (const sourceId of [...known]) {
|
|
7572
|
+
if (bySource.has(sourceId)) continue;
|
|
7573
|
+
known.delete(sourceId);
|
|
7574
|
+
await this.unload({ kind, sourceId });
|
|
7575
|
+
}
|
|
7576
|
+
});
|
|
7577
|
+
this.commitQueue = next.catch(() => void 0);
|
|
7578
|
+
return next;
|
|
7579
|
+
}
|
|
7432
7580
|
get extensionHost() {
|
|
7433
7581
|
return this.extensions.extensionHost;
|
|
7434
7582
|
}
|
|
@@ -7444,8 +7592,9 @@ var RuntimeBootstrapRegistry = class extends ResourceRegistry {
|
|
|
7444
7592
|
})();
|
|
7445
7593
|
const normalized = await loaded;
|
|
7446
7594
|
const result = await this.extensions.activate(normalized.extensions);
|
|
7447
|
-
await this.
|
|
7448
|
-
await this.
|
|
7595
|
+
await this.recommit("tool");
|
|
7596
|
+
await this.recommit("phase");
|
|
7597
|
+
await this.recommit("skill");
|
|
7449
7598
|
return {
|
|
7450
7599
|
...result,
|
|
7451
7600
|
revision: `extensions:${Date.now()}`,
|
|
@@ -12984,6 +13133,7 @@ export {
|
|
|
12984
13133
|
createCoreTools2 as createCoreTools,
|
|
12985
13134
|
createDefaultPhase,
|
|
12986
13135
|
createStopPhase,
|
|
13136
|
+
extensionSourceId,
|
|
12987
13137
|
isConfigurationSnapshot,
|
|
12988
13138
|
isRuntimeError,
|
|
12989
13139
|
loadExtensionsFromPath as loadExtensions,
|