@harness-engineering/orchestrator 0.7.0 → 0.8.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.mts CHANGED
@@ -1,10 +1,11 @@
1
1
  import * as _harness_engineering_types from '@harness-engineering/types';
2
- import { Issue, AgentEvent, WorkflowConfig, TokenUsage, ConcernSignal, ScopeTier, EscalationConfig, IssueRoutingDecision, Result, WorkflowDefinition, BackendDef, RoutingConfig, WorkspaceConfig, HooksConfig, AgentBackend, SessionStartParams, AgentSession, AgentError, TurnParams, TurnResult, CheckScriptDefinition, OutputRetentionConfig, RoutingDecision, RoutingUseCase, ContainerConfig, SecretConfig, AgentConfig, CustomTaskDefinition, TokenScope, AuthToken, AuthTokenPublic, IndexedFileKind, SessionSearchResult, ReindexStats, SessionSummarizationConfig, SessionSummary, SessionSummaryMeta, SessionsConfig, GatewayEvent, NotificationEnvelope, NotificationDeliveryResult, NotificationSinkConfig, NotificationsConfig } from '@harness-engineering/types';
2
+ import { Issue, AgentEvent, WorkflowConfig, TokenUsage, ConcernSignal, ScopeTier, EscalationConfig, IssueRoutingDecision, Result, WorkflowDefinition, BackendDef, RoutingConfig, WorkspaceConfig, HooksConfig, AgentBackend, SessionStartParams, AgentSession, AgentError, TurnParams, TurnResult, CheckScriptDefinition, OutputRetentionConfig, RoutingDecision, RoutingUseCase, ContainerConfig, SecretConfig, AgentConfig, LocalModelStatus, CustomTaskDefinition, TokenScope, AuthToken, AuthTokenPublic, IndexedFileKind, SessionSearchResult, ReindexStats, SessionSummarizationConfig, SessionSummary, SessionSummaryMeta, SessionsConfig, GatewayEvent, NotificationEnvelope, NotificationDeliveryResult, NotificationSinkConfig, NotificationsConfig } from '@harness-engineering/types';
3
3
  import { IssueTrackerClient, Issue as Issue$1, TrackerConfig, CacheMetricsRecorder, ArchiveHooks, SkillProposal, ProposalGateFinding } from '@harness-engineering/core';
4
4
  import { EnrichedSpec, ComplexityScore, SimulationResult, IntelligencePipeline, WeightedRecommendation, AnalysisProvider } from '@harness-engineering/intelligence';
5
5
  import { GraphStore } from '@harness-engineering/graph';
6
6
  import { execFile } from 'node:child_process';
7
7
  import { EventEmitter } from 'node:events';
8
+ import { z } from 'zod';
8
9
 
9
10
  /**
10
11
  * Run attempt lifecycle phases (internal to orchestrator).
@@ -1921,6 +1922,270 @@ interface CreateBackendOptions {
1921
1922
  */
1922
1923
  declare function createBackend(def: BackendDef, options?: CreateBackendOptions): AgentBackend;
1923
1924
 
1925
+ /**
1926
+ * Zod schema for `BackendDef` (Spec 2 — multi-backend routing).
1927
+ *
1928
+ * Discriminated union on `type`. Per-variant validation surfaces shape
1929
+ * mismatches (missing `model`, missing `endpoint`, etc.) at config-load
1930
+ * time rather than at orchestrator runtime.
1931
+ *
1932
+ * Used in Phase 3 by `validateWorkflowConfig`; in Phase 1 it is exported
1933
+ * for standalone unit testing.
1934
+ */
1935
+ declare const BackendDefSchema: z.ZodDiscriminatedUnion<"type", [z.ZodObject<{
1936
+ type: z.ZodLiteral<"mock">;
1937
+ }, "strict", z.ZodTypeAny, {
1938
+ type: "mock";
1939
+ }, {
1940
+ type: "mock";
1941
+ }>, z.ZodObject<{
1942
+ type: z.ZodLiteral<"claude">;
1943
+ command: z.ZodOptional<z.ZodString>;
1944
+ }, "strict", z.ZodTypeAny, {
1945
+ type: "claude";
1946
+ command?: string | undefined;
1947
+ }, {
1948
+ type: "claude";
1949
+ command?: string | undefined;
1950
+ }>, z.ZodObject<{
1951
+ type: z.ZodLiteral<"anthropic">;
1952
+ model: z.ZodString;
1953
+ apiKey: z.ZodOptional<z.ZodString>;
1954
+ }, "strict", z.ZodTypeAny, {
1955
+ type: "anthropic";
1956
+ model: string;
1957
+ apiKey?: string | undefined;
1958
+ }, {
1959
+ type: "anthropic";
1960
+ model: string;
1961
+ apiKey?: string | undefined;
1962
+ }>, z.ZodObject<{
1963
+ type: z.ZodLiteral<"openai">;
1964
+ model: z.ZodString;
1965
+ apiKey: z.ZodOptional<z.ZodString>;
1966
+ }, "strict", z.ZodTypeAny, {
1967
+ type: "openai";
1968
+ model: string;
1969
+ apiKey?: string | undefined;
1970
+ }, {
1971
+ type: "openai";
1972
+ model: string;
1973
+ apiKey?: string | undefined;
1974
+ }>, z.ZodObject<{
1975
+ type: z.ZodLiteral<"gemini">;
1976
+ model: z.ZodString;
1977
+ apiKey: z.ZodOptional<z.ZodString>;
1978
+ }, "strict", z.ZodTypeAny, {
1979
+ type: "gemini";
1980
+ model: string;
1981
+ apiKey?: string | undefined;
1982
+ }, {
1983
+ type: "gemini";
1984
+ model: string;
1985
+ apiKey?: string | undefined;
1986
+ }>, z.ZodObject<{
1987
+ type: z.ZodLiteral<"local">;
1988
+ endpoint: z.ZodString;
1989
+ model: z.ZodUnion<[z.ZodString, z.ZodArray<z.ZodString, "atleastone">]>;
1990
+ apiKey: z.ZodOptional<z.ZodString>;
1991
+ timeoutMs: z.ZodOptional<z.ZodNumber>;
1992
+ probeIntervalMs: z.ZodOptional<z.ZodNumber>;
1993
+ }, "strict", z.ZodTypeAny, {
1994
+ type: "local";
1995
+ model: string | [string, ...string[]];
1996
+ endpoint: string;
1997
+ apiKey?: string | undefined;
1998
+ timeoutMs?: number | undefined;
1999
+ probeIntervalMs?: number | undefined;
2000
+ }, {
2001
+ type: "local";
2002
+ model: string | [string, ...string[]];
2003
+ endpoint: string;
2004
+ apiKey?: string | undefined;
2005
+ timeoutMs?: number | undefined;
2006
+ probeIntervalMs?: number | undefined;
2007
+ }>, z.ZodObject<{
2008
+ type: z.ZodLiteral<"pi">;
2009
+ endpoint: z.ZodString;
2010
+ model: z.ZodUnion<[z.ZodString, z.ZodArray<z.ZodString, "atleastone">]>;
2011
+ apiKey: z.ZodOptional<z.ZodString>;
2012
+ timeoutMs: z.ZodOptional<z.ZodNumber>;
2013
+ probeIntervalMs: z.ZodOptional<z.ZodNumber>;
2014
+ }, "strict", z.ZodTypeAny, {
2015
+ type: "pi";
2016
+ model: string | [string, ...string[]];
2017
+ endpoint: string;
2018
+ apiKey?: string | undefined;
2019
+ timeoutMs?: number | undefined;
2020
+ probeIntervalMs?: number | undefined;
2021
+ }, {
2022
+ type: "pi";
2023
+ model: string | [string, ...string[]];
2024
+ endpoint: string;
2025
+ apiKey?: string | undefined;
2026
+ timeoutMs?: number | undefined;
2027
+ probeIntervalMs?: number | undefined;
2028
+ }>]>;
2029
+ /**
2030
+ * Spec B Phase 0: a routing target is either a backend name (scalar
2031
+ * string) or a non-empty ordered fallback chain (string tuple). The
2032
+ * scalar form is byte-compatible with pre-Spec-B configs.
2033
+ */
2034
+ declare const RoutingValueSchema: z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>;
2035
+ /**
2036
+ * Zod schema for `RoutingConfig`. `.strict()` rejects unknown keys at
2037
+ * every level (per Spec 2 D7: typos in routing keys are validation
2038
+ * errors, not silent default-fallthroughs).
2039
+ *
2040
+ * Spec B Phase 0: all scalar routing fields accept `RoutingValueSchema`
2041
+ * (scalar or non-empty chain). New optional `skills` and `modes` maps
2042
+ * accept the same.
2043
+ *
2044
+ * Spec B Phase 2: the `isolation` block (added to the TS interface in
2045
+ * Hermes Phase 5 but not previously in this Zod schema) is now included
2046
+ * here with each tier widened to `RoutingValueSchema`. This closes the
2047
+ * Phase 0 I2 review finding (TS-vs-Zod drift) and ensures isolation
2048
+ * chain entries are validated by the same cross-field check that
2049
+ * covers `skills` / `modes`.
2050
+ */
2051
+ declare const RoutingConfigSchema: z.ZodObject<{
2052
+ default: z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>;
2053
+ 'quick-fix': z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2054
+ 'guided-change': z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2055
+ 'full-exploration': z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2056
+ diagnostic: z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2057
+ intelligence: z.ZodOptional<z.ZodObject<{
2058
+ sel: z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2059
+ pesl: z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2060
+ }, "strict", z.ZodTypeAny, {
2061
+ sel?: string | readonly [string, ...string[]] | undefined;
2062
+ pesl?: string | readonly [string, ...string[]] | undefined;
2063
+ }, {
2064
+ sel?: string | readonly [string, ...string[]] | undefined;
2065
+ pesl?: string | readonly [string, ...string[]] | undefined;
2066
+ }>>;
2067
+ isolation: z.ZodOptional<z.ZodObject<{
2068
+ none: z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2069
+ container: z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2070
+ 'remote-sandbox': z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2071
+ }, "strict", z.ZodTypeAny, {
2072
+ none?: string | readonly [string, ...string[]] | undefined;
2073
+ container?: string | readonly [string, ...string[]] | undefined;
2074
+ 'remote-sandbox'?: string | readonly [string, ...string[]] | undefined;
2075
+ }, {
2076
+ none?: string | readonly [string, ...string[]] | undefined;
2077
+ container?: string | readonly [string, ...string[]] | undefined;
2078
+ 'remote-sandbox'?: string | readonly [string, ...string[]] | undefined;
2079
+ }>>;
2080
+ skills: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>>;
2081
+ modes: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>>;
2082
+ }, "strict", z.ZodTypeAny, {
2083
+ default: string | readonly [string, ...string[]];
2084
+ 'quick-fix'?: string | readonly [string, ...string[]] | undefined;
2085
+ 'guided-change'?: string | readonly [string, ...string[]] | undefined;
2086
+ 'full-exploration'?: string | readonly [string, ...string[]] | undefined;
2087
+ diagnostic?: string | readonly [string, ...string[]] | undefined;
2088
+ intelligence?: {
2089
+ sel?: string | readonly [string, ...string[]] | undefined;
2090
+ pesl?: string | readonly [string, ...string[]] | undefined;
2091
+ } | undefined;
2092
+ isolation?: {
2093
+ none?: string | readonly [string, ...string[]] | undefined;
2094
+ container?: string | readonly [string, ...string[]] | undefined;
2095
+ 'remote-sandbox'?: string | readonly [string, ...string[]] | undefined;
2096
+ } | undefined;
2097
+ skills?: Record<string, string | readonly [string, ...string[]]> | undefined;
2098
+ modes?: Record<string, string | readonly [string, ...string[]]> | undefined;
2099
+ }, {
2100
+ default: string | readonly [string, ...string[]];
2101
+ 'quick-fix'?: string | readonly [string, ...string[]] | undefined;
2102
+ 'guided-change'?: string | readonly [string, ...string[]] | undefined;
2103
+ 'full-exploration'?: string | readonly [string, ...string[]] | undefined;
2104
+ diagnostic?: string | readonly [string, ...string[]] | undefined;
2105
+ intelligence?: {
2106
+ sel?: string | readonly [string, ...string[]] | undefined;
2107
+ pesl?: string | readonly [string, ...string[]] | undefined;
2108
+ } | undefined;
2109
+ isolation?: {
2110
+ none?: string | readonly [string, ...string[]] | undefined;
2111
+ container?: string | readonly [string, ...string[]] | undefined;
2112
+ 'remote-sandbox'?: string | readonly [string, ...string[]] | undefined;
2113
+ } | undefined;
2114
+ skills?: Record<string, string | readonly [string, ...string[]]> | undefined;
2115
+ modes?: Record<string, string | readonly [string, ...string[]]> | undefined;
2116
+ }>;
2117
+
2118
+ interface ResolverLogger {
2119
+ info(message: string, context?: Record<string, unknown>): void;
2120
+ warn(message: string, context?: Record<string, unknown>): void;
2121
+ }
2122
+ interface LocalModelResolverOptions {
2123
+ endpoint: string;
2124
+ apiKey?: string;
2125
+ /** Normalized candidate list (already turned from string|string[] into string[]). */
2126
+ configured: string[];
2127
+ /** Probe cadence in ms; default 30_000, minimum 1_000. */
2128
+ probeIntervalMs?: number;
2129
+ /**
2130
+ * Per-request timeout for the default fetch implementation, in ms.
2131
+ * Default: 5_000. Ignored when a custom `fetchModels` is provided
2132
+ * (custom impls own their own timeout policy). Spec §3.1 line 136
2133
+ * enumerates timeout as a supported failure mode.
2134
+ */
2135
+ timeoutMs?: number;
2136
+ /**
2137
+ * Injectable for tests. Default: GET `${endpoint}/models` with bearer apiKey.
2138
+ * Resolves to detected model IDs. Rejects on network/timeout/non-2xx/malformed.
2139
+ */
2140
+ fetchModels?: (endpoint: string, apiKey?: string) => Promise<string[]>;
2141
+ logger?: ResolverLogger;
2142
+ }
2143
+ declare function normalizeLocalModel(input: string | string[] | undefined): string[];
2144
+ /**
2145
+ * Default `fetchModels` — GET `${endpoint}/models` with bearer apiKey.
2146
+ * Throws on network failure, non-2xx, malformed body, or timeout.
2147
+ *
2148
+ * `timeoutMs` defaults to 5_000. A timeout aborts the in-flight request and
2149
+ * surfaces as `Error('request timeout (Nms)')` so callers can distinguish it
2150
+ * from generic network errors.
2151
+ */
2152
+ declare function defaultFetchModels(endpoint: string, apiKey?: string, timeoutMs?: number): Promise<string[]>;
2153
+ declare class LocalModelResolver {
2154
+ private readonly endpoint;
2155
+ private readonly apiKey?;
2156
+ private readonly configured;
2157
+ private readonly probeIntervalMs;
2158
+ private readonly fetchModels;
2159
+ private readonly logger;
2160
+ private timer;
2161
+ private listeners;
2162
+ /**
2163
+ * Tracks an in-flight probe so concurrent invocations (interval tick while a
2164
+ * slow probe is running, or a manual `probe()` call mid-flight) share the
2165
+ * existing promise instead of racing to mutate `detected/resolved/lastError/
2166
+ * warnings` non-atomically across `await` points. Applies to both the timer
2167
+ * callback and direct `probe()` calls — any caller that arrives during an
2168
+ * in-flight probe gets the same promise back. Cleared in `finally` so the
2169
+ * next tick can start a fresh probe.
2170
+ */
2171
+ private probeInFlight;
2172
+ private resolved;
2173
+ private detected;
2174
+ private lastProbeAt;
2175
+ private lastError;
2176
+ private warnings;
2177
+ private available;
2178
+ constructor(opts: LocalModelResolverOptions);
2179
+ resolveModel(): string | null;
2180
+ getStatus(): LocalModelStatus;
2181
+ onStatusChange(handler: (status: LocalModelStatus) => void): () => void;
2182
+ probe(): Promise<LocalModelStatus>;
2183
+ private runProbe;
2184
+ start(): Promise<void>;
2185
+ stop(): void;
2186
+ private snapshotForDiff;
2187
+ }
2188
+
1924
2189
  /**
1925
2190
  * Function signature compatible with Node's `child_process.execFile`.
1926
2191
  * Allows injection for testing.
@@ -2552,4 +2817,4 @@ declare function emitProposalCreated(bus: EventEmitter, proposal: SkillProposal)
2552
2817
  declare function emitProposalApproved(bus: EventEmitter, proposal: SkillProposal): void;
2553
2818
  declare function emitProposalRejected(bus: EventEmitter, proposal: SkillProposal): void;
2554
2819
 
2555
- export { type AgentUpdateEvent, AnalysisArchive, type AnalysisRecord, type ApplyEventResult, type ArtifactPresence, type AttemptStats, BUILT_IN_TASKS, BackendRouter, type BackendRouterOptions, type BaseRefFallbackEvent, type BuildArchiveHooksOptions, ClaimManager, type ClaimManagerConfig, type CleanWorkspaceEffect, type CreateTokenInput, type CreateTokenResult, type CustomTaskValidationError, type DispatchEffect, type EmitLogEffect, type EscalateEffect, type ExecFileFn$1 as ExecFileFn, type FromConfigOptions, GateNotReadyError, type GateResult, GateRunError, type Highlight, type HighlightsInfo, type IndexedDoc, InteractionQueue, type LinearGraphQLExtension, LinearGraphQLStub, type LiveSession, MAX_ATTEMPTS, type MigrationResult, MockBackend, type NotificationSink, type NotificationSinkDeliverInput, ORCHESTRATOR_IDENTITY_FILE, Orchestrator, OrchestratorBackendFactory, type OrchestratorBackendFactoryOptions, type OrchestratorContext, type OrchestratorEvent, type OrchestratorState, PRDetector, type PRDetectorLogger, type PendingInteraction, type PersistedOutputEntry, PromotionError, type PromotionResult, PromptRenderer, type ProposalApprovedData, type ProposalCreatedData, type ProposalRejectedData, type PublishedIndex, type QueueInsertInput, type QueueRow, type QueueStats, RETRY_DELAYS_MS, type RateLimitSnapshot as RateLimitComputeSnapshot, type RateLimitConfig, type RateLimitSnapshot$1 as RateLimitSnapshot, type RegistryEntry, type ReleaseClaimEffect, type RetryEntry, type RetryFiredEvent, RoadmapTrackerAdapter, type RunAttemptPhase, type RunOrigin, type RunningEntry, type ScheduleRetryEffect, type SearchOptions, type SideEffect, SinkConfigError, SinkRegistry, type SkillCatalogEntry, SlackSink, type SlackSinkOptions, SqliteSearchIndex, type StallDetectedEvent, type StopEffect, type StreamManifest, StreamRecorder, type SummarizeContext, type SummarizeResult, type SyncMainOptions, type SyncMainResult, type SyncSkipReason, type TaskDefinition, TaskOutputStore, type TaskType, type TickEvent, TokenStore, type TokenTotals, type TriageConfig, type TriageDecision, type TriageSignals, type TriageSkill, type UpdateTokensEffect, type ValidateWorkflowConfigOptions, type ValidatedWorkflowConfig, WebhookQueue, type WorkerExitEvent, WorkflowLoader, WorkspaceHooks, WorkspaceManager, type WorkspaceManagerOptions, applyEvent, artifactPresenceFromIssue, buildArchiveHooks, calculateRetryDelay, canDispatch, computeRateLimitDelay, createBackend, createEmptyState, crossFieldRoutingIssues, detectScopeTier, discoverSkillCatalog, discoverSkillCatalogNames, emitProposalApproved, emitProposalCreated, emitProposalRejected, extractHighlights, extractTitlePrefix, getAvailableSlots, getDefaultConfig, getPerStateCount, indexSessionDirectory, isEligible, isSummaryEnabled, launchTUI, loadPublishedIndex, migrateAgentConfig, normalizeFts5Query, openSearchIndex, promote, reconcile, reindexFromArchive, renderAnalysisComment, renderLlmSummaryMarkdown, renderPRComment, resolveEscalationConfig, resolveOrchestratorId, routeIssue, routingWarnings, runGate, savePublishedIndex, searchIndexPath, selectCandidates, sortCandidates, summarizeArchivedSession, syncMain, triageIssue, truncateForBudget, validateCustomTasks, validateWorkflowConfig, wireNotificationSinks, wrapAsEnvelope };
2820
+ export { type AgentUpdateEvent, AnalysisArchive, type AnalysisRecord, type ApplyEventResult, type ArtifactPresence, type AttemptStats, BUILT_IN_TASKS, BackendDefSchema, BackendRouter, type BackendRouterOptions, type BaseRefFallbackEvent, type BuildArchiveHooksOptions, ClaimManager, type ClaimManagerConfig, type CleanWorkspaceEffect, type CreateTokenInput, type CreateTokenResult, type CustomTaskValidationError, type DispatchEffect, type EmitLogEffect, type EscalateEffect, type ExecFileFn$1 as ExecFileFn, type FromConfigOptions, GateNotReadyError, type GateResult, GateRunError, type Highlight, type HighlightsInfo, type IndexedDoc, InteractionQueue, type LinearGraphQLExtension, LinearGraphQLStub, type LiveSession, LocalModelResolver, type LocalModelResolverOptions, MAX_ATTEMPTS, type MigrationResult, MockBackend, type NotificationSink, type NotificationSinkDeliverInput, ORCHESTRATOR_IDENTITY_FILE, Orchestrator, OrchestratorBackendFactory, type OrchestratorBackendFactoryOptions, type OrchestratorContext, type OrchestratorEvent, type OrchestratorState, PRDetector, type PRDetectorLogger, type PendingInteraction, type PersistedOutputEntry, PromotionError, type PromotionResult, PromptRenderer, type ProposalApprovedData, type ProposalCreatedData, type ProposalRejectedData, type PublishedIndex, type QueueInsertInput, type QueueRow, type QueueStats, RETRY_DELAYS_MS, type RateLimitSnapshot as RateLimitComputeSnapshot, type RateLimitConfig, type RateLimitSnapshot$1 as RateLimitSnapshot, type RegistryEntry, type ReleaseClaimEffect, type ResolverLogger, type RetryEntry, type RetryFiredEvent, RoadmapTrackerAdapter, RoutingConfigSchema, RoutingValueSchema, type RunAttemptPhase, type RunOrigin, type RunningEntry, type ScheduleRetryEffect, type SearchOptions, type SideEffect, SinkConfigError, SinkRegistry, type SkillCatalogEntry, SlackSink, type SlackSinkOptions, SqliteSearchIndex, type StallDetectedEvent, type StopEffect, type StreamManifest, StreamRecorder, type SummarizeContext, type SummarizeResult, type SyncMainOptions, type SyncMainResult, type SyncSkipReason, type TaskDefinition, TaskOutputStore, type TaskType, type TickEvent, TokenStore, type TokenTotals, type TriageConfig, type TriageDecision, type TriageSignals, type TriageSkill, type UpdateTokensEffect, type ValidateWorkflowConfigOptions, type ValidatedWorkflowConfig, WebhookQueue, type WorkerExitEvent, WorkflowLoader, WorkspaceHooks, WorkspaceManager, type WorkspaceManagerOptions, applyEvent, artifactPresenceFromIssue, buildArchiveHooks, calculateRetryDelay, canDispatch, computeRateLimitDelay, createBackend, createEmptyState, crossFieldRoutingIssues, defaultFetchModels, detectScopeTier, discoverSkillCatalog, discoverSkillCatalogNames, emitProposalApproved, emitProposalCreated, emitProposalRejected, extractHighlights, extractTitlePrefix, getAvailableSlots, getDefaultConfig, getPerStateCount, indexSessionDirectory, isEligible, isSummaryEnabled, launchTUI, loadPublishedIndex, migrateAgentConfig, normalizeFts5Query, normalizeLocalModel, openSearchIndex, promote, reconcile, reindexFromArchive, renderAnalysisComment, renderLlmSummaryMarkdown, renderPRComment, resolveEscalationConfig, resolveOrchestratorId, routeIssue, routingWarnings, runGate, savePublishedIndex, searchIndexPath, selectCandidates, sortCandidates, summarizeArchivedSession, syncMain, triageIssue, truncateForBudget, validateCustomTasks, validateWorkflowConfig, wireNotificationSinks, wrapAsEnvelope };
package/dist/index.d.ts CHANGED
@@ -1,10 +1,11 @@
1
1
  import * as _harness_engineering_types from '@harness-engineering/types';
2
- import { Issue, AgentEvent, WorkflowConfig, TokenUsage, ConcernSignal, ScopeTier, EscalationConfig, IssueRoutingDecision, Result, WorkflowDefinition, BackendDef, RoutingConfig, WorkspaceConfig, HooksConfig, AgentBackend, SessionStartParams, AgentSession, AgentError, TurnParams, TurnResult, CheckScriptDefinition, OutputRetentionConfig, RoutingDecision, RoutingUseCase, ContainerConfig, SecretConfig, AgentConfig, CustomTaskDefinition, TokenScope, AuthToken, AuthTokenPublic, IndexedFileKind, SessionSearchResult, ReindexStats, SessionSummarizationConfig, SessionSummary, SessionSummaryMeta, SessionsConfig, GatewayEvent, NotificationEnvelope, NotificationDeliveryResult, NotificationSinkConfig, NotificationsConfig } from '@harness-engineering/types';
2
+ import { Issue, AgentEvent, WorkflowConfig, TokenUsage, ConcernSignal, ScopeTier, EscalationConfig, IssueRoutingDecision, Result, WorkflowDefinition, BackendDef, RoutingConfig, WorkspaceConfig, HooksConfig, AgentBackend, SessionStartParams, AgentSession, AgentError, TurnParams, TurnResult, CheckScriptDefinition, OutputRetentionConfig, RoutingDecision, RoutingUseCase, ContainerConfig, SecretConfig, AgentConfig, LocalModelStatus, CustomTaskDefinition, TokenScope, AuthToken, AuthTokenPublic, IndexedFileKind, SessionSearchResult, ReindexStats, SessionSummarizationConfig, SessionSummary, SessionSummaryMeta, SessionsConfig, GatewayEvent, NotificationEnvelope, NotificationDeliveryResult, NotificationSinkConfig, NotificationsConfig } from '@harness-engineering/types';
3
3
  import { IssueTrackerClient, Issue as Issue$1, TrackerConfig, CacheMetricsRecorder, ArchiveHooks, SkillProposal, ProposalGateFinding } from '@harness-engineering/core';
4
4
  import { EnrichedSpec, ComplexityScore, SimulationResult, IntelligencePipeline, WeightedRecommendation, AnalysisProvider } from '@harness-engineering/intelligence';
5
5
  import { GraphStore } from '@harness-engineering/graph';
6
6
  import { execFile } from 'node:child_process';
7
7
  import { EventEmitter } from 'node:events';
8
+ import { z } from 'zod';
8
9
 
9
10
  /**
10
11
  * Run attempt lifecycle phases (internal to orchestrator).
@@ -1921,6 +1922,270 @@ interface CreateBackendOptions {
1921
1922
  */
1922
1923
  declare function createBackend(def: BackendDef, options?: CreateBackendOptions): AgentBackend;
1923
1924
 
1925
+ /**
1926
+ * Zod schema for `BackendDef` (Spec 2 — multi-backend routing).
1927
+ *
1928
+ * Discriminated union on `type`. Per-variant validation surfaces shape
1929
+ * mismatches (missing `model`, missing `endpoint`, etc.) at config-load
1930
+ * time rather than at orchestrator runtime.
1931
+ *
1932
+ * Used in Phase 3 by `validateWorkflowConfig`; in Phase 1 it is exported
1933
+ * for standalone unit testing.
1934
+ */
1935
+ declare const BackendDefSchema: z.ZodDiscriminatedUnion<"type", [z.ZodObject<{
1936
+ type: z.ZodLiteral<"mock">;
1937
+ }, "strict", z.ZodTypeAny, {
1938
+ type: "mock";
1939
+ }, {
1940
+ type: "mock";
1941
+ }>, z.ZodObject<{
1942
+ type: z.ZodLiteral<"claude">;
1943
+ command: z.ZodOptional<z.ZodString>;
1944
+ }, "strict", z.ZodTypeAny, {
1945
+ type: "claude";
1946
+ command?: string | undefined;
1947
+ }, {
1948
+ type: "claude";
1949
+ command?: string | undefined;
1950
+ }>, z.ZodObject<{
1951
+ type: z.ZodLiteral<"anthropic">;
1952
+ model: z.ZodString;
1953
+ apiKey: z.ZodOptional<z.ZodString>;
1954
+ }, "strict", z.ZodTypeAny, {
1955
+ type: "anthropic";
1956
+ model: string;
1957
+ apiKey?: string | undefined;
1958
+ }, {
1959
+ type: "anthropic";
1960
+ model: string;
1961
+ apiKey?: string | undefined;
1962
+ }>, z.ZodObject<{
1963
+ type: z.ZodLiteral<"openai">;
1964
+ model: z.ZodString;
1965
+ apiKey: z.ZodOptional<z.ZodString>;
1966
+ }, "strict", z.ZodTypeAny, {
1967
+ type: "openai";
1968
+ model: string;
1969
+ apiKey?: string | undefined;
1970
+ }, {
1971
+ type: "openai";
1972
+ model: string;
1973
+ apiKey?: string | undefined;
1974
+ }>, z.ZodObject<{
1975
+ type: z.ZodLiteral<"gemini">;
1976
+ model: z.ZodString;
1977
+ apiKey: z.ZodOptional<z.ZodString>;
1978
+ }, "strict", z.ZodTypeAny, {
1979
+ type: "gemini";
1980
+ model: string;
1981
+ apiKey?: string | undefined;
1982
+ }, {
1983
+ type: "gemini";
1984
+ model: string;
1985
+ apiKey?: string | undefined;
1986
+ }>, z.ZodObject<{
1987
+ type: z.ZodLiteral<"local">;
1988
+ endpoint: z.ZodString;
1989
+ model: z.ZodUnion<[z.ZodString, z.ZodArray<z.ZodString, "atleastone">]>;
1990
+ apiKey: z.ZodOptional<z.ZodString>;
1991
+ timeoutMs: z.ZodOptional<z.ZodNumber>;
1992
+ probeIntervalMs: z.ZodOptional<z.ZodNumber>;
1993
+ }, "strict", z.ZodTypeAny, {
1994
+ type: "local";
1995
+ model: string | [string, ...string[]];
1996
+ endpoint: string;
1997
+ apiKey?: string | undefined;
1998
+ timeoutMs?: number | undefined;
1999
+ probeIntervalMs?: number | undefined;
2000
+ }, {
2001
+ type: "local";
2002
+ model: string | [string, ...string[]];
2003
+ endpoint: string;
2004
+ apiKey?: string | undefined;
2005
+ timeoutMs?: number | undefined;
2006
+ probeIntervalMs?: number | undefined;
2007
+ }>, z.ZodObject<{
2008
+ type: z.ZodLiteral<"pi">;
2009
+ endpoint: z.ZodString;
2010
+ model: z.ZodUnion<[z.ZodString, z.ZodArray<z.ZodString, "atleastone">]>;
2011
+ apiKey: z.ZodOptional<z.ZodString>;
2012
+ timeoutMs: z.ZodOptional<z.ZodNumber>;
2013
+ probeIntervalMs: z.ZodOptional<z.ZodNumber>;
2014
+ }, "strict", z.ZodTypeAny, {
2015
+ type: "pi";
2016
+ model: string | [string, ...string[]];
2017
+ endpoint: string;
2018
+ apiKey?: string | undefined;
2019
+ timeoutMs?: number | undefined;
2020
+ probeIntervalMs?: number | undefined;
2021
+ }, {
2022
+ type: "pi";
2023
+ model: string | [string, ...string[]];
2024
+ endpoint: string;
2025
+ apiKey?: string | undefined;
2026
+ timeoutMs?: number | undefined;
2027
+ probeIntervalMs?: number | undefined;
2028
+ }>]>;
2029
+ /**
2030
+ * Spec B Phase 0: a routing target is either a backend name (scalar
2031
+ * string) or a non-empty ordered fallback chain (string tuple). The
2032
+ * scalar form is byte-compatible with pre-Spec-B configs.
2033
+ */
2034
+ declare const RoutingValueSchema: z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>;
2035
+ /**
2036
+ * Zod schema for `RoutingConfig`. `.strict()` rejects unknown keys at
2037
+ * every level (per Spec 2 D7: typos in routing keys are validation
2038
+ * errors, not silent default-fallthroughs).
2039
+ *
2040
+ * Spec B Phase 0: all scalar routing fields accept `RoutingValueSchema`
2041
+ * (scalar or non-empty chain). New optional `skills` and `modes` maps
2042
+ * accept the same.
2043
+ *
2044
+ * Spec B Phase 2: the `isolation` block (added to the TS interface in
2045
+ * Hermes Phase 5 but not previously in this Zod schema) is now included
2046
+ * here with each tier widened to `RoutingValueSchema`. This closes the
2047
+ * Phase 0 I2 review finding (TS-vs-Zod drift) and ensures isolation
2048
+ * chain entries are validated by the same cross-field check that
2049
+ * covers `skills` / `modes`.
2050
+ */
2051
+ declare const RoutingConfigSchema: z.ZodObject<{
2052
+ default: z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>;
2053
+ 'quick-fix': z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2054
+ 'guided-change': z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2055
+ 'full-exploration': z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2056
+ diagnostic: z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2057
+ intelligence: z.ZodOptional<z.ZodObject<{
2058
+ sel: z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2059
+ pesl: z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2060
+ }, "strict", z.ZodTypeAny, {
2061
+ sel?: string | readonly [string, ...string[]] | undefined;
2062
+ pesl?: string | readonly [string, ...string[]] | undefined;
2063
+ }, {
2064
+ sel?: string | readonly [string, ...string[]] | undefined;
2065
+ pesl?: string | readonly [string, ...string[]] | undefined;
2066
+ }>>;
2067
+ isolation: z.ZodOptional<z.ZodObject<{
2068
+ none: z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2069
+ container: z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2070
+ 'remote-sandbox': z.ZodOptional<z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>;
2071
+ }, "strict", z.ZodTypeAny, {
2072
+ none?: string | readonly [string, ...string[]] | undefined;
2073
+ container?: string | readonly [string, ...string[]] | undefined;
2074
+ 'remote-sandbox'?: string | readonly [string, ...string[]] | undefined;
2075
+ }, {
2076
+ none?: string | readonly [string, ...string[]] | undefined;
2077
+ container?: string | readonly [string, ...string[]] | undefined;
2078
+ 'remote-sandbox'?: string | readonly [string, ...string[]] | undefined;
2079
+ }>>;
2080
+ skills: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>>;
2081
+ modes: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnion<[z.ZodString, z.ZodReadonly<z.ZodArray<z.ZodString, "atleastone">>]>>>;
2082
+ }, "strict", z.ZodTypeAny, {
2083
+ default: string | readonly [string, ...string[]];
2084
+ 'quick-fix'?: string | readonly [string, ...string[]] | undefined;
2085
+ 'guided-change'?: string | readonly [string, ...string[]] | undefined;
2086
+ 'full-exploration'?: string | readonly [string, ...string[]] | undefined;
2087
+ diagnostic?: string | readonly [string, ...string[]] | undefined;
2088
+ intelligence?: {
2089
+ sel?: string | readonly [string, ...string[]] | undefined;
2090
+ pesl?: string | readonly [string, ...string[]] | undefined;
2091
+ } | undefined;
2092
+ isolation?: {
2093
+ none?: string | readonly [string, ...string[]] | undefined;
2094
+ container?: string | readonly [string, ...string[]] | undefined;
2095
+ 'remote-sandbox'?: string | readonly [string, ...string[]] | undefined;
2096
+ } | undefined;
2097
+ skills?: Record<string, string | readonly [string, ...string[]]> | undefined;
2098
+ modes?: Record<string, string | readonly [string, ...string[]]> | undefined;
2099
+ }, {
2100
+ default: string | readonly [string, ...string[]];
2101
+ 'quick-fix'?: string | readonly [string, ...string[]] | undefined;
2102
+ 'guided-change'?: string | readonly [string, ...string[]] | undefined;
2103
+ 'full-exploration'?: string | readonly [string, ...string[]] | undefined;
2104
+ diagnostic?: string | readonly [string, ...string[]] | undefined;
2105
+ intelligence?: {
2106
+ sel?: string | readonly [string, ...string[]] | undefined;
2107
+ pesl?: string | readonly [string, ...string[]] | undefined;
2108
+ } | undefined;
2109
+ isolation?: {
2110
+ none?: string | readonly [string, ...string[]] | undefined;
2111
+ container?: string | readonly [string, ...string[]] | undefined;
2112
+ 'remote-sandbox'?: string | readonly [string, ...string[]] | undefined;
2113
+ } | undefined;
2114
+ skills?: Record<string, string | readonly [string, ...string[]]> | undefined;
2115
+ modes?: Record<string, string | readonly [string, ...string[]]> | undefined;
2116
+ }>;
2117
+
2118
+ interface ResolverLogger {
2119
+ info(message: string, context?: Record<string, unknown>): void;
2120
+ warn(message: string, context?: Record<string, unknown>): void;
2121
+ }
2122
+ interface LocalModelResolverOptions {
2123
+ endpoint: string;
2124
+ apiKey?: string;
2125
+ /** Normalized candidate list (already turned from string|string[] into string[]). */
2126
+ configured: string[];
2127
+ /** Probe cadence in ms; default 30_000, minimum 1_000. */
2128
+ probeIntervalMs?: number;
2129
+ /**
2130
+ * Per-request timeout for the default fetch implementation, in ms.
2131
+ * Default: 5_000. Ignored when a custom `fetchModels` is provided
2132
+ * (custom impls own their own timeout policy). Spec §3.1 line 136
2133
+ * enumerates timeout as a supported failure mode.
2134
+ */
2135
+ timeoutMs?: number;
2136
+ /**
2137
+ * Injectable for tests. Default: GET `${endpoint}/models` with bearer apiKey.
2138
+ * Resolves to detected model IDs. Rejects on network/timeout/non-2xx/malformed.
2139
+ */
2140
+ fetchModels?: (endpoint: string, apiKey?: string) => Promise<string[]>;
2141
+ logger?: ResolverLogger;
2142
+ }
2143
+ declare function normalizeLocalModel(input: string | string[] | undefined): string[];
2144
+ /**
2145
+ * Default `fetchModels` — GET `${endpoint}/models` with bearer apiKey.
2146
+ * Throws on network failure, non-2xx, malformed body, or timeout.
2147
+ *
2148
+ * `timeoutMs` defaults to 5_000. A timeout aborts the in-flight request and
2149
+ * surfaces as `Error('request timeout (Nms)')` so callers can distinguish it
2150
+ * from generic network errors.
2151
+ */
2152
+ declare function defaultFetchModels(endpoint: string, apiKey?: string, timeoutMs?: number): Promise<string[]>;
2153
+ declare class LocalModelResolver {
2154
+ private readonly endpoint;
2155
+ private readonly apiKey?;
2156
+ private readonly configured;
2157
+ private readonly probeIntervalMs;
2158
+ private readonly fetchModels;
2159
+ private readonly logger;
2160
+ private timer;
2161
+ private listeners;
2162
+ /**
2163
+ * Tracks an in-flight probe so concurrent invocations (interval tick while a
2164
+ * slow probe is running, or a manual `probe()` call mid-flight) share the
2165
+ * existing promise instead of racing to mutate `detected/resolved/lastError/
2166
+ * warnings` non-atomically across `await` points. Applies to both the timer
2167
+ * callback and direct `probe()` calls — any caller that arrives during an
2168
+ * in-flight probe gets the same promise back. Cleared in `finally` so the
2169
+ * next tick can start a fresh probe.
2170
+ */
2171
+ private probeInFlight;
2172
+ private resolved;
2173
+ private detected;
2174
+ private lastProbeAt;
2175
+ private lastError;
2176
+ private warnings;
2177
+ private available;
2178
+ constructor(opts: LocalModelResolverOptions);
2179
+ resolveModel(): string | null;
2180
+ getStatus(): LocalModelStatus;
2181
+ onStatusChange(handler: (status: LocalModelStatus) => void): () => void;
2182
+ probe(): Promise<LocalModelStatus>;
2183
+ private runProbe;
2184
+ start(): Promise<void>;
2185
+ stop(): void;
2186
+ private snapshotForDiff;
2187
+ }
2188
+
1924
2189
  /**
1925
2190
  * Function signature compatible with Node's `child_process.execFile`.
1926
2191
  * Allows injection for testing.
@@ -2552,4 +2817,4 @@ declare function emitProposalCreated(bus: EventEmitter, proposal: SkillProposal)
2552
2817
  declare function emitProposalApproved(bus: EventEmitter, proposal: SkillProposal): void;
2553
2818
  declare function emitProposalRejected(bus: EventEmitter, proposal: SkillProposal): void;
2554
2819
 
2555
- export { type AgentUpdateEvent, AnalysisArchive, type AnalysisRecord, type ApplyEventResult, type ArtifactPresence, type AttemptStats, BUILT_IN_TASKS, BackendRouter, type BackendRouterOptions, type BaseRefFallbackEvent, type BuildArchiveHooksOptions, ClaimManager, type ClaimManagerConfig, type CleanWorkspaceEffect, type CreateTokenInput, type CreateTokenResult, type CustomTaskValidationError, type DispatchEffect, type EmitLogEffect, type EscalateEffect, type ExecFileFn$1 as ExecFileFn, type FromConfigOptions, GateNotReadyError, type GateResult, GateRunError, type Highlight, type HighlightsInfo, type IndexedDoc, InteractionQueue, type LinearGraphQLExtension, LinearGraphQLStub, type LiveSession, MAX_ATTEMPTS, type MigrationResult, MockBackend, type NotificationSink, type NotificationSinkDeliverInput, ORCHESTRATOR_IDENTITY_FILE, Orchestrator, OrchestratorBackendFactory, type OrchestratorBackendFactoryOptions, type OrchestratorContext, type OrchestratorEvent, type OrchestratorState, PRDetector, type PRDetectorLogger, type PendingInteraction, type PersistedOutputEntry, PromotionError, type PromotionResult, PromptRenderer, type ProposalApprovedData, type ProposalCreatedData, type ProposalRejectedData, type PublishedIndex, type QueueInsertInput, type QueueRow, type QueueStats, RETRY_DELAYS_MS, type RateLimitSnapshot as RateLimitComputeSnapshot, type RateLimitConfig, type RateLimitSnapshot$1 as RateLimitSnapshot, type RegistryEntry, type ReleaseClaimEffect, type RetryEntry, type RetryFiredEvent, RoadmapTrackerAdapter, type RunAttemptPhase, type RunOrigin, type RunningEntry, type ScheduleRetryEffect, type SearchOptions, type SideEffect, SinkConfigError, SinkRegistry, type SkillCatalogEntry, SlackSink, type SlackSinkOptions, SqliteSearchIndex, type StallDetectedEvent, type StopEffect, type StreamManifest, StreamRecorder, type SummarizeContext, type SummarizeResult, type SyncMainOptions, type SyncMainResult, type SyncSkipReason, type TaskDefinition, TaskOutputStore, type TaskType, type TickEvent, TokenStore, type TokenTotals, type TriageConfig, type TriageDecision, type TriageSignals, type TriageSkill, type UpdateTokensEffect, type ValidateWorkflowConfigOptions, type ValidatedWorkflowConfig, WebhookQueue, type WorkerExitEvent, WorkflowLoader, WorkspaceHooks, WorkspaceManager, type WorkspaceManagerOptions, applyEvent, artifactPresenceFromIssue, buildArchiveHooks, calculateRetryDelay, canDispatch, computeRateLimitDelay, createBackend, createEmptyState, crossFieldRoutingIssues, detectScopeTier, discoverSkillCatalog, discoverSkillCatalogNames, emitProposalApproved, emitProposalCreated, emitProposalRejected, extractHighlights, extractTitlePrefix, getAvailableSlots, getDefaultConfig, getPerStateCount, indexSessionDirectory, isEligible, isSummaryEnabled, launchTUI, loadPublishedIndex, migrateAgentConfig, normalizeFts5Query, openSearchIndex, promote, reconcile, reindexFromArchive, renderAnalysisComment, renderLlmSummaryMarkdown, renderPRComment, resolveEscalationConfig, resolveOrchestratorId, routeIssue, routingWarnings, runGate, savePublishedIndex, searchIndexPath, selectCandidates, sortCandidates, summarizeArchivedSession, syncMain, triageIssue, truncateForBudget, validateCustomTasks, validateWorkflowConfig, wireNotificationSinks, wrapAsEnvelope };
2820
+ export { type AgentUpdateEvent, AnalysisArchive, type AnalysisRecord, type ApplyEventResult, type ArtifactPresence, type AttemptStats, BUILT_IN_TASKS, BackendDefSchema, BackendRouter, type BackendRouterOptions, type BaseRefFallbackEvent, type BuildArchiveHooksOptions, ClaimManager, type ClaimManagerConfig, type CleanWorkspaceEffect, type CreateTokenInput, type CreateTokenResult, type CustomTaskValidationError, type DispatchEffect, type EmitLogEffect, type EscalateEffect, type ExecFileFn$1 as ExecFileFn, type FromConfigOptions, GateNotReadyError, type GateResult, GateRunError, type Highlight, type HighlightsInfo, type IndexedDoc, InteractionQueue, type LinearGraphQLExtension, LinearGraphQLStub, type LiveSession, LocalModelResolver, type LocalModelResolverOptions, MAX_ATTEMPTS, type MigrationResult, MockBackend, type NotificationSink, type NotificationSinkDeliverInput, ORCHESTRATOR_IDENTITY_FILE, Orchestrator, OrchestratorBackendFactory, type OrchestratorBackendFactoryOptions, type OrchestratorContext, type OrchestratorEvent, type OrchestratorState, PRDetector, type PRDetectorLogger, type PendingInteraction, type PersistedOutputEntry, PromotionError, type PromotionResult, PromptRenderer, type ProposalApprovedData, type ProposalCreatedData, type ProposalRejectedData, type PublishedIndex, type QueueInsertInput, type QueueRow, type QueueStats, RETRY_DELAYS_MS, type RateLimitSnapshot as RateLimitComputeSnapshot, type RateLimitConfig, type RateLimitSnapshot$1 as RateLimitSnapshot, type RegistryEntry, type ReleaseClaimEffect, type ResolverLogger, type RetryEntry, type RetryFiredEvent, RoadmapTrackerAdapter, RoutingConfigSchema, RoutingValueSchema, type RunAttemptPhase, type RunOrigin, type RunningEntry, type ScheduleRetryEffect, type SearchOptions, type SideEffect, SinkConfigError, SinkRegistry, type SkillCatalogEntry, SlackSink, type SlackSinkOptions, SqliteSearchIndex, type StallDetectedEvent, type StopEffect, type StreamManifest, StreamRecorder, type SummarizeContext, type SummarizeResult, type SyncMainOptions, type SyncMainResult, type SyncSkipReason, type TaskDefinition, TaskOutputStore, type TaskType, type TickEvent, TokenStore, type TokenTotals, type TriageConfig, type TriageDecision, type TriageSignals, type TriageSkill, type UpdateTokensEffect, type ValidateWorkflowConfigOptions, type ValidatedWorkflowConfig, WebhookQueue, type WorkerExitEvent, WorkflowLoader, WorkspaceHooks, WorkspaceManager, type WorkspaceManagerOptions, applyEvent, artifactPresenceFromIssue, buildArchiveHooks, calculateRetryDelay, canDispatch, computeRateLimitDelay, createBackend, createEmptyState, crossFieldRoutingIssues, defaultFetchModels, detectScopeTier, discoverSkillCatalog, discoverSkillCatalogNames, emitProposalApproved, emitProposalCreated, emitProposalRejected, extractHighlights, extractTitlePrefix, getAvailableSlots, getDefaultConfig, getPerStateCount, indexSessionDirectory, isEligible, isSummaryEnabled, launchTUI, loadPublishedIndex, migrateAgentConfig, normalizeFts5Query, normalizeLocalModel, openSearchIndex, promote, reconcile, reindexFromArchive, renderAnalysisComment, renderLlmSummaryMarkdown, renderPRComment, resolveEscalationConfig, resolveOrchestratorId, routeIssue, routingWarnings, runGate, savePublishedIndex, searchIndexPath, selectCandidates, sortCandidates, summarizeArchivedSession, syncMain, triageIssue, truncateForBudget, validateCustomTasks, validateWorkflowConfig, wireNotificationSinks, wrapAsEnvelope };
package/dist/index.js CHANGED
@@ -32,12 +32,14 @@ var index_exports = {};
32
32
  __export(index_exports, {
33
33
  AnalysisArchive: () => AnalysisArchive,
34
34
  BUILT_IN_TASKS: () => BUILT_IN_TASKS,
35
+ BackendDefSchema: () => BackendDefSchema,
35
36
  BackendRouter: () => BackendRouter,
36
37
  ClaimManager: () => ClaimManager,
37
38
  GateNotReadyError: () => GateNotReadyError,
38
39
  GateRunError: () => GateRunError,
39
40
  InteractionQueue: () => InteractionQueue,
40
41
  LinearGraphQLStub: () => LinearGraphQLStub,
42
+ LocalModelResolver: () => LocalModelResolver,
41
43
  MAX_ATTEMPTS: () => MAX_ATTEMPTS,
42
44
  MockBackend: () => MockBackend,
43
45
  ORCHESTRATOR_IDENTITY_FILE: () => ORCHESTRATOR_IDENTITY_FILE,
@@ -48,6 +50,8 @@ __export(index_exports, {
48
50
  PromptRenderer: () => PromptRenderer,
49
51
  RETRY_DELAYS_MS: () => RETRY_DELAYS_MS,
50
52
  RoadmapTrackerAdapter: () => RoadmapTrackerAdapter,
53
+ RoutingConfigSchema: () => RoutingConfigSchema,
54
+ RoutingValueSchema: () => RoutingValueSchema,
51
55
  SinkConfigError: () => SinkConfigError,
52
56
  SinkRegistry: () => SinkRegistry,
53
57
  SlackSink: () => SlackSink,
@@ -68,6 +72,7 @@ __export(index_exports, {
68
72
  createBackend: () => createBackend,
69
73
  createEmptyState: () => createEmptyState,
70
74
  crossFieldRoutingIssues: () => crossFieldRoutingIssues,
75
+ defaultFetchModels: () => defaultFetchModels,
71
76
  detectScopeTier: () => detectScopeTier,
72
77
  discoverSkillCatalog: () => discoverSkillCatalog,
73
78
  discoverSkillCatalogNames: () => discoverSkillCatalogNames,
@@ -86,6 +91,7 @@ __export(index_exports, {
86
91
  loadPublishedIndex: () => loadPublishedIndex,
87
92
  migrateAgentConfig: () => migrateAgentConfig,
88
93
  normalizeFts5Query: () => normalizeFts5Query,
94
+ normalizeLocalModel: () => normalizeLocalModel,
89
95
  openSearchIndex: () => openSearchIndex,
90
96
  promote: () => promote,
91
97
  reconcile: () => reconcile,
@@ -3640,6 +3646,14 @@ var DEFAULT_PROBE_INTERVAL_MS = 3e4;
3640
3646
  var MIN_PROBE_INTERVAL_MS = 1e3;
3641
3647
  var DEFAULT_API_KEY = "lm-studio";
3642
3648
  var DEFAULT_FETCH_TIMEOUT_MS = 5e3;
3649
+ function normalizeLocalModel(input) {
3650
+ if (input === void 0) return [];
3651
+ if (typeof input === "string") return [input];
3652
+ if (input.length === 0) {
3653
+ throw new Error("localModel array must be non-empty when provided");
3654
+ }
3655
+ return [...input];
3656
+ }
3643
3657
  var noopLogger = {
3644
3658
  info: () => void 0,
3645
3659
  warn: () => void 0
@@ -14689,12 +14703,14 @@ function buildArchiveHooks(opts) {
14689
14703
  0 && (module.exports = {
14690
14704
  AnalysisArchive,
14691
14705
  BUILT_IN_TASKS,
14706
+ BackendDefSchema,
14692
14707
  BackendRouter,
14693
14708
  ClaimManager,
14694
14709
  GateNotReadyError,
14695
14710
  GateRunError,
14696
14711
  InteractionQueue,
14697
14712
  LinearGraphQLStub,
14713
+ LocalModelResolver,
14698
14714
  MAX_ATTEMPTS,
14699
14715
  MockBackend,
14700
14716
  ORCHESTRATOR_IDENTITY_FILE,
@@ -14705,6 +14721,8 @@ function buildArchiveHooks(opts) {
14705
14721
  PromptRenderer,
14706
14722
  RETRY_DELAYS_MS,
14707
14723
  RoadmapTrackerAdapter,
14724
+ RoutingConfigSchema,
14725
+ RoutingValueSchema,
14708
14726
  SinkConfigError,
14709
14727
  SinkRegistry,
14710
14728
  SlackSink,
@@ -14725,6 +14743,7 @@ function buildArchiveHooks(opts) {
14725
14743
  createBackend,
14726
14744
  createEmptyState,
14727
14745
  crossFieldRoutingIssues,
14746
+ defaultFetchModels,
14728
14747
  detectScopeTier,
14729
14748
  discoverSkillCatalog,
14730
14749
  discoverSkillCatalogNames,
@@ -14743,6 +14762,7 @@ function buildArchiveHooks(opts) {
14743
14762
  loadPublishedIndex,
14744
14763
  migrateAgentConfig,
14745
14764
  normalizeFts5Query,
14765
+ normalizeLocalModel,
14746
14766
  openSearchIndex,
14747
14767
  promote,
14748
14768
  reconcile,
package/dist/index.mjs CHANGED
@@ -3544,6 +3544,14 @@ var DEFAULT_PROBE_INTERVAL_MS = 3e4;
3544
3544
  var MIN_PROBE_INTERVAL_MS = 1e3;
3545
3545
  var DEFAULT_API_KEY = "lm-studio";
3546
3546
  var DEFAULT_FETCH_TIMEOUT_MS = 5e3;
3547
+ function normalizeLocalModel(input) {
3548
+ if (input === void 0) return [];
3549
+ if (typeof input === "string") return [input];
3550
+ if (input.length === 0) {
3551
+ throw new Error("localModel array must be non-empty when provided");
3552
+ }
3553
+ return [...input];
3554
+ }
3547
3555
  var noopLogger = {
3548
3556
  info: () => void 0,
3549
3557
  warn: () => void 0
@@ -14667,12 +14675,14 @@ function buildArchiveHooks(opts) {
14667
14675
  export {
14668
14676
  AnalysisArchive,
14669
14677
  BUILT_IN_TASKS,
14678
+ BackendDefSchema,
14670
14679
  BackendRouter,
14671
14680
  ClaimManager,
14672
14681
  GateNotReadyError,
14673
14682
  GateRunError,
14674
14683
  InteractionQueue,
14675
14684
  LinearGraphQLStub,
14685
+ LocalModelResolver,
14676
14686
  MAX_ATTEMPTS,
14677
14687
  MockBackend,
14678
14688
  ORCHESTRATOR_IDENTITY_FILE,
@@ -14683,6 +14693,8 @@ export {
14683
14693
  PromptRenderer,
14684
14694
  RETRY_DELAYS_MS,
14685
14695
  RoadmapTrackerAdapter,
14696
+ RoutingConfigSchema,
14697
+ RoutingValueSchema,
14686
14698
  SinkConfigError,
14687
14699
  SinkRegistry,
14688
14700
  SlackSink,
@@ -14703,6 +14715,7 @@ export {
14703
14715
  createBackend,
14704
14716
  createEmptyState,
14705
14717
  crossFieldRoutingIssues,
14718
+ defaultFetchModels,
14706
14719
  detectScopeTier,
14707
14720
  discoverSkillCatalog,
14708
14721
  discoverSkillCatalogNames,
@@ -14721,6 +14734,7 @@ export {
14721
14734
  loadPublishedIndex,
14722
14735
  migrateAgentConfig,
14723
14736
  normalizeFts5Query,
14737
+ normalizeLocalModel,
14724
14738
  openSearchIndex,
14725
14739
  promote,
14726
14740
  reconcile,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@harness-engineering/orchestrator",
3
- "version": "0.7.0",
3
+ "version": "0.8.0",
4
4
  "description": "Orchestrator daemon for dispatching coding agents to issues",
5
5
  "main": "./dist/index.js",
6
6
  "module": "./dist/index.mjs",
@@ -48,10 +48,10 @@
48
48
  "ws": "^8.21.0",
49
49
  "yaml": "^2.8.3",
50
50
  "zod": "^3.25.76",
51
- "@harness-engineering/core": "0.28.1",
52
- "@harness-engineering/graph": "0.10.0",
51
+ "@harness-engineering/core": "0.28.2",
53
52
  "@harness-engineering/intelligence": "0.2.6",
54
- "@harness-engineering/types": "0.15.0"
53
+ "@harness-engineering/types": "0.15.0",
54
+ "@harness-engineering/graph": "0.10.0"
55
55
  },
56
56
  "devDependencies": {
57
57
  "@asteasolutions/zod-to-openapi": "^7.3.0",