@lota-sdk/core 0.4.9 → 0.4.11
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/package.json +2 -2
- package/src/ai/embedding-cache.ts +3 -1
- package/src/ai-gateway/ai-gateway.ts +164 -82
- package/src/ai-gateway/index.ts +16 -1
- package/src/config/agent-defaults.ts +4 -107
- package/src/config/agent-types.ts +1 -1
- package/src/config/background-processing.ts +1 -1
- package/src/config/index.ts +0 -1
- package/src/config/logger.ts +22 -25
- package/src/config/thread-defaults.ts +1 -10
- package/src/create-runtime.ts +145 -670
- package/src/db/base.service.ts +30 -38
- package/src/db/memory-query-builder.ts +2 -1
- package/src/db/memory-store.ts +29 -20
- package/src/db/memory.ts +188 -195
- package/src/db/service-normalization.ts +97 -64
- package/src/db/service.ts +496 -384
- package/src/db/startup.ts +30 -19
- package/src/effect/helpers.ts +30 -5
- package/src/effect/index.ts +7 -7
- package/src/effect/layers.ts +75 -72
- package/src/effect/services.ts +15 -11
- package/src/embeddings/provider.ts +65 -71
- package/src/index.ts +13 -12
- package/src/queues/autonomous-job.queue.ts +177 -143
- package/src/queues/context-compaction.queue.ts +41 -39
- package/src/queues/delayed-node-promotion.queue.ts +61 -42
- package/src/queues/document-processor.queue.ts +5 -3
- package/src/queues/index.ts +1 -0
- package/src/queues/memory-consolidation.queue.ts +79 -53
- package/src/queues/organization-learning.queue.ts +70 -33
- package/src/queues/plan-agent-heartbeat.queue.ts +111 -83
- package/src/queues/plan-scheduler.queue.ts +101 -97
- package/src/queues/post-chat-memory.queue.ts +56 -46
- package/src/queues/queue-factory.ts +146 -69
- package/src/queues/queues.service.ts +61 -0
- package/src/queues/title-generation.queue.ts +44 -44
- package/src/redis/connection.ts +181 -164
- package/src/redis/org-memory-lock.ts +24 -9
- package/src/redis/redis-lease-lock.ts +8 -1
- package/src/redis/stream-context.ts +17 -9
- package/src/runtime/agent-identity-overrides.ts +7 -3
- package/src/runtime/agent-runtime-policy.ts +10 -5
- package/src/runtime/agent-stream-helpers.ts +24 -15
- package/src/runtime/chat-run-orchestration.ts +1 -1
- package/src/runtime/context-compaction/context-compaction-runtime.ts +28 -32
- package/src/runtime/context-compaction/context-compaction.ts +131 -85
- package/src/runtime/domain-layer.ts +203 -0
- package/src/runtime/execution-plan-visibility.ts +5 -2
- package/src/runtime/graph-designer.ts +0 -14
- package/src/runtime/helper-model.ts +8 -4
- package/src/runtime/index.ts +1 -1
- package/src/runtime/indexed-repositories-policy.ts +2 -6
- package/src/runtime/memory/memory-block.ts +19 -9
- package/src/runtime/memory/memory-pipeline.ts +53 -66
- package/src/runtime/memory/memory-scope.ts +33 -29
- package/src/runtime/plugin-resolution.ts +58 -62
- package/src/runtime/post-turn-side-effects.ts +139 -161
- package/src/runtime/retrieval-adapters.ts +4 -4
- package/src/runtime/runtime-config.ts +3 -9
- package/src/runtime/runtime-extensions.ts +0 -43
- package/src/runtime/runtime-lifecycle.ts +124 -0
- package/src/runtime/runtime-services.ts +455 -0
- package/src/runtime/runtime-worker-registry.ts +113 -30
- package/src/runtime/social-chat/social-chat-agent-runner.ts +13 -8
- package/src/runtime/social-chat/social-chat-history.ts +24 -13
- package/src/runtime/social-chat/social-chat.ts +420 -369
- package/src/runtime/team-consultation/team-consultation-orchestrator.ts +64 -57
- package/src/runtime/team-consultation/team-consultation-prompts.ts +11 -6
- package/src/runtime/thread-chat-helpers.ts +18 -9
- package/src/runtime/thread-turn-context.ts +28 -74
- package/src/runtime/turn-lifecycle.ts +6 -14
- package/src/services/agent-activity.service.ts +169 -176
- package/src/services/agent-executor.service.ts +207 -196
- package/src/services/artifact.service.ts +10 -5
- package/src/services/attachment.service.ts +16 -48
- package/src/services/autonomous-job.service.ts +81 -87
- package/src/services/background-work.service.ts +54 -0
- package/src/services/chat-run-registry.service.ts +3 -1
- package/src/services/context-compaction.service.ts +8 -10
- package/src/services/document-chunk.service.ts +8 -17
- package/src/services/execution-plan/execution-plan-graph.ts +122 -109
- package/src/services/execution-plan/execution-plan-schedule.ts +1 -15
- package/src/services/execution-plan/execution-plan.service.ts +68 -51
- package/src/services/feedback-loop.service.ts +1 -1
- package/src/services/global-orchestrator.service.ts +49 -15
- package/src/services/graph-full-routing.ts +49 -37
- package/src/services/index.ts +1 -0
- package/src/services/institutional-memory.service.ts +8 -17
- package/src/services/learned-skill.service.ts +38 -35
- package/src/services/memory/memory-conversation.ts +10 -5
- package/src/services/memory/memory-errors.ts +27 -0
- package/src/services/memory/memory-org-memory.ts +14 -3
- package/src/services/memory/memory-preseeded.ts +10 -4
- package/src/services/memory/memory-utils.ts +2 -1
- package/src/services/memory/memory.service.ts +37 -52
- package/src/services/memory/rerank.service.ts +3 -11
- package/src/services/monitoring-window.service.ts +1 -1
- package/src/services/mutating-approval.service.ts +1 -1
- package/src/services/node-workspace.service.ts +2 -2
- package/src/services/notification.service.ts +16 -4
- package/src/services/organization-member.service.ts +1 -1
- package/src/services/organization.service.ts +34 -51
- package/src/services/ownership-dispatcher.service.ts +148 -95
- package/src/services/plan/plan-agent-heartbeat.service.ts +30 -16
- package/src/services/plan/plan-agent-query.service.ts +13 -9
- package/src/services/plan/plan-approval.service.ts +52 -48
- package/src/services/plan/plan-artifact.service.ts +2 -2
- package/src/services/plan/plan-builder.service.ts +2 -2
- package/src/services/plan/plan-checkpoint.service.ts +1 -1
- package/src/services/plan/plan-compiler.service.ts +1 -1
- package/src/services/plan/plan-completion-side-effects.ts +99 -113
- package/src/services/plan/plan-coordination.service.ts +1 -1
- package/src/services/plan/plan-cycle.service.ts +171 -202
- package/src/services/plan/plan-deadline.service.ts +304 -307
- package/src/services/plan/plan-event-delivery.service.ts +84 -72
- package/src/services/plan/plan-executor-context.ts +2 -0
- package/src/services/plan/plan-executor-graph.ts +375 -353
- package/src/services/plan/plan-executor-helpers.ts +60 -75
- package/src/services/plan/plan-executor.service.ts +494 -489
- package/src/services/plan/plan-run.service.ts +12 -19
- package/src/services/plan/plan-scheduler.service.ts +89 -82
- package/src/services/plan/plan-template.service.ts +1 -1
- package/src/services/plan/plan-transaction-events.ts +8 -5
- package/src/services/plan/plan-validator.service.ts +1 -1
- package/src/services/plan/plan-workspace.service.ts +17 -11
- package/src/services/plugin-executor.service.ts +26 -21
- package/src/services/quality-metrics.service.ts +1 -1
- package/src/services/queue-job.service.ts +8 -17
- package/src/services/recent-activity-title.service.ts +22 -10
- package/src/services/recent-activity.service.ts +1 -1
- package/src/services/skill-resolver.service.ts +1 -1
- package/src/services/social-chat-history.service.ts +37 -20
- package/src/services/system-executor.service.ts +25 -20
- package/src/services/thread/thread-bootstrap.ts +37 -19
- package/src/services/thread/thread-listing.ts +2 -1
- package/src/services/thread/thread-memory-block.ts +18 -5
- package/src/services/thread/thread-message.service.ts +30 -13
- package/src/services/thread/thread-title.service.ts +1 -1
- package/src/services/thread/thread-turn-execution.ts +87 -83
- package/src/services/thread/thread-turn-preparation.service.ts +65 -40
- package/src/services/thread/thread-turn-streaming.ts +32 -36
- package/src/services/thread/thread-turn.ts +43 -29
- package/src/services/thread/thread.service.ts +32 -8
- package/src/services/user.service.ts +1 -1
- package/src/services/write-intent-validator.service.ts +1 -1
- package/src/storage/attachment-storage.service.ts +7 -4
- package/src/storage/generated-document-storage.service.ts +1 -1
- package/src/system-agents/context-compaction.agent.ts +1 -1
- package/src/system-agents/helper-agent-options.ts +1 -1
- package/src/system-agents/memory-reranker.agent.ts +1 -1
- package/src/system-agents/memory.agent.ts +1 -1
- package/src/system-agents/recent-activity-title-refiner.agent.ts +9 -6
- package/src/system-agents/regular-chat-memory-digest.agent.ts +1 -1
- package/src/system-agents/skill-extractor.agent.ts +1 -1
- package/src/system-agents/skill-manager.agent.ts +1 -1
- package/src/system-agents/thread-router.agent.ts +23 -20
- package/src/system-agents/title-generator.agent.ts +1 -1
- package/src/tools/execution-plan.tool.ts +36 -20
- package/src/tools/fetch-webpage.tool.ts +30 -22
- package/src/tools/firecrawl-client.ts +1 -6
- package/src/tools/plan-approval.tool.ts +9 -1
- package/src/tools/remember-memory.tool.ts +3 -6
- package/src/tools/research-topic.tool.ts +12 -3
- package/src/tools/search-web.tool.ts +26 -18
- package/src/tools/search.tool.ts +4 -5
- package/src/tools/team-think.tool.ts +139 -121
- package/src/utils/async.ts +15 -6
- package/src/utils/errors.ts +27 -15
- package/src/workers/bootstrap.ts +34 -58
- package/src/workers/memory-consolidation.worker.ts +4 -1
- package/src/workers/organization-learning.worker.ts +16 -3
- package/src/workers/regular-chat-memory-digest.helpers.ts +3 -4
- package/src/workers/regular-chat-memory-digest.runner.ts +46 -29
- package/src/workers/skill-extraction.runner.ts +13 -15
- package/src/workers/worker-utils.ts +14 -8
- package/src/config/search.ts +0 -3
- package/src/effect/awaitable-effect.ts +0 -87
- package/src/effect/runtime-ref.ts +0 -25
- package/src/effect/runtime.ts +0 -31
- package/src/redis/runtime-connection.ts +0 -10
- package/src/runtime/agent-types.ts +0 -1
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import type { ChatMessage } from '@lota-sdk/shared'
|
|
2
2
|
import type { LanguageModelUsage, UIMessageStreamOptions } from 'ai'
|
|
3
|
-
import { Duration, Effect,
|
|
3
|
+
import { Duration, Effect, Exit, Scope } from 'effect'
|
|
4
4
|
|
|
5
|
-
import {
|
|
5
|
+
import type { ResolvedAgentConfig } from '../config/agent-defaults'
|
|
6
6
|
import { nowEpochMillis } from '../utils/date-time'
|
|
7
7
|
import { readRecord as _readRecord } from '../utils/string'
|
|
8
8
|
|
|
@@ -106,17 +106,20 @@ export function createTimedAbortSignal(parentSignal: AbortSignal, timeoutMs: num
|
|
|
106
106
|
const abortFromParent = () => {
|
|
107
107
|
controller.abort((parentSignal as AbortSignal & { reason?: unknown }).reason)
|
|
108
108
|
}
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
109
|
+
|
|
110
|
+
// Own a scope so the timeout fiber is cleaned up via Scope.close() on dispose,
|
|
111
|
+
// matching Effect v4 best practices (forkScoped + scope-bound finalizers).
|
|
112
|
+
const scope = Scope.makeUnsafe()
|
|
113
|
+
const timeoutEffect = Effect.sleep(Duration.millis(timeoutMs)).pipe(
|
|
114
|
+
Effect.andThen(
|
|
115
|
+
Effect.sync(() => {
|
|
116
|
+
if (disposed || controller.signal.aborted) return
|
|
117
|
+
didTimeout = true
|
|
118
|
+
controller.abort(new Error(`Timed out after ${timeoutMs}ms`))
|
|
119
|
+
}),
|
|
118
120
|
),
|
|
119
121
|
)
|
|
122
|
+
Effect.runFork(Scope.provide(Effect.forkScoped(timeoutEffect), scope))
|
|
120
123
|
|
|
121
124
|
if (parentSignal.aborted) {
|
|
122
125
|
abortFromParent()
|
|
@@ -128,16 +131,22 @@ export function createTimedAbortSignal(parentSignal: AbortSignal, timeoutMs: num
|
|
|
128
131
|
signal: controller.signal,
|
|
129
132
|
didTimeout: () => didTimeout,
|
|
130
133
|
dispose: () => {
|
|
134
|
+
if (disposed) return
|
|
131
135
|
disposed = true
|
|
132
136
|
parentSignal.removeEventListener('abort', abortFromParent)
|
|
133
|
-
void Effect.
|
|
137
|
+
void Effect.runPromise(Scope.close(scope, Exit.void).pipe(Effect.catchCause(() => Effect.void)))
|
|
134
138
|
},
|
|
135
139
|
}
|
|
136
140
|
}
|
|
137
141
|
|
|
138
|
-
export function buildSpecialistTaskMessage(params: {
|
|
139
|
-
|
|
140
|
-
|
|
142
|
+
export function buildSpecialistTaskMessage(params: {
|
|
143
|
+
agentConfig: ResolvedAgentConfig
|
|
144
|
+
agentId: string
|
|
145
|
+
task: string
|
|
146
|
+
}): ChatMessage {
|
|
147
|
+
const displayName = params.agentConfig.displayNames[params.agentId] ?? params.agentId
|
|
148
|
+
const leadAgentDisplayName =
|
|
149
|
+
params.agentConfig.displayNames[params.agentConfig.leadAgentId] ?? params.agentConfig.leadAgentId
|
|
141
150
|
return {
|
|
142
151
|
id: Bun.randomUUIDv7(),
|
|
143
152
|
role: 'user',
|
|
@@ -37,7 +37,7 @@ interface CompactionCoordination {
|
|
|
37
37
|
}
|
|
38
38
|
|
|
39
39
|
export class CompactionCoordinationTag extends Context.Service<CompactionCoordinationTag, CompactionCoordination>()(
|
|
40
|
-
'CompactionCoordination',
|
|
40
|
+
'@lota-sdk/core/CompactionCoordination',
|
|
41
41
|
) {}
|
|
42
42
|
|
|
43
43
|
export const CompactionCoordinationLive = Layer.effect(
|
|
@@ -48,33 +48,31 @@ function tryContextCompactionPromise<A>(
|
|
|
48
48
|
})
|
|
49
49
|
}
|
|
50
50
|
|
|
51
|
-
function
|
|
52
|
-
return
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
).pipe(Effect.map(parseCompactionOutput)),
|
|
70
|
-
)
|
|
51
|
+
function runContextCompacterEffect(helperModelRuntime: HelperModelRuntime, params: ContextCompactionRunnerParams) {
|
|
52
|
+
return tryContextCompactionPromise('Failed to compact runtime context.', () =>
|
|
53
|
+
helperModelRuntime.generateHelperStructured({
|
|
54
|
+
tag: 'context-compaction',
|
|
55
|
+
createAgent: createContextCompactionAgent,
|
|
56
|
+
messages: [
|
|
57
|
+
{
|
|
58
|
+
role: 'user',
|
|
59
|
+
content: buildContextCompactionPrompt({
|
|
60
|
+
previousSummary: params.previousSummary,
|
|
61
|
+
transcript: params.transcript,
|
|
62
|
+
}),
|
|
63
|
+
},
|
|
64
|
+
],
|
|
65
|
+
schema: ContextCompactionOutputSchema,
|
|
66
|
+
maxOutputTokens: 8_000,
|
|
67
|
+
}),
|
|
68
|
+
).pipe(Effect.flatMap(parseCompactionOutput))
|
|
71
69
|
}
|
|
72
70
|
|
|
73
71
|
export function createWiredContextCompactionRuntime(deps: CreateContextCompactionRuntimeDeps) {
|
|
74
72
|
const { helperModelRuntime } = deps
|
|
75
73
|
|
|
76
74
|
const runtime = createContextCompactionRuntime({
|
|
77
|
-
runCompacter: (params) =>
|
|
75
|
+
runCompacter: (params) => runContextCompacterEffect(helperModelRuntime, params),
|
|
78
76
|
now: deps.now,
|
|
79
77
|
randomId: deps.randomId,
|
|
80
78
|
thresholdRatio: CONTEXT_COMPACTION_THRESHOLD_RATIO,
|
|
@@ -86,20 +84,18 @@ export function createWiredContextCompactionRuntime(deps: CreateContextCompactio
|
|
|
86
84
|
includedToolPrefixes: CONTEXT_COMPACTION_INCLUDED_TOOL_PREFIXES,
|
|
87
85
|
})
|
|
88
86
|
|
|
89
|
-
function compactMemoryBlockSummary(params: { previousSummary: string; newEntriesText: string })
|
|
87
|
+
function compactMemoryBlockSummary(params: { previousSummary: string; newEntriesText: string }) {
|
|
90
88
|
const previousSummary = params.previousSummary.trim()
|
|
91
89
|
const newEntriesText = params.newEntriesText.trim()
|
|
92
|
-
if (!previousSummary && !newEntriesText) return
|
|
90
|
+
if (!previousSummary && !newEntriesText) return Effect.succeed('')
|
|
93
91
|
|
|
94
|
-
return
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
}),
|
|
102
|
-
),
|
|
92
|
+
return tryContextCompactionPromise('Failed to compact memory block summary.', () =>
|
|
93
|
+
helperModelRuntime.generateHelperText({
|
|
94
|
+
tag: 'memory-block-compaction',
|
|
95
|
+
createAgent: createContextCompactionAgent,
|
|
96
|
+
messages: [{ role: 'user', content: buildMemoryBlockCompactionPrompt({ previousSummary, newEntriesText }) }],
|
|
97
|
+
maxOutputTokens: CONTEXT_COMPACTION_MAX_OUTPUT_TOKENS,
|
|
98
|
+
}),
|
|
103
99
|
)
|
|
104
100
|
}
|
|
105
101
|
|
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
import type { ChatMessage } from '@lota-sdk/shared'
|
|
2
|
-
import {
|
|
2
|
+
import { Duration, Effect, Schedule, Schema } from 'effect'
|
|
3
3
|
import { z } from 'zod'
|
|
4
4
|
|
|
5
|
+
import { iterateEffect } from '../../effect/helpers'
|
|
5
6
|
import { nowEpochMillis } from '../../utils/date-time'
|
|
6
7
|
import {
|
|
7
8
|
CHARS_PER_TOKEN_ESTIMATE,
|
|
@@ -64,6 +65,13 @@ class CompactionError extends Schema.TaggedErrorClass<CompactionError>()('Compac
|
|
|
64
65
|
cause: Schema.optional(Schema.Defect),
|
|
65
66
|
}) {}
|
|
66
67
|
|
|
68
|
+
class CompactionParseError extends Schema.TaggedErrorClass<CompactionParseError>()('CompactionParseError', {
|
|
69
|
+
message: Schema.String,
|
|
70
|
+
cause: Schema.optional(Schema.Defect),
|
|
71
|
+
}) {}
|
|
72
|
+
|
|
73
|
+
const COMPACTION_RUNNER_RETRY_OPTIONS = { times: 2, schedule: Schedule.exponential(Duration.millis(500), 2) } as const
|
|
74
|
+
|
|
67
75
|
export interface ContextCompactionPromptParams {
|
|
68
76
|
previousSummary: string
|
|
69
77
|
transcript: string
|
|
@@ -80,7 +88,9 @@ export interface CompactionOutput {
|
|
|
80
88
|
summary: string
|
|
81
89
|
}
|
|
82
90
|
|
|
83
|
-
export type ContextCompactionRunner = (
|
|
91
|
+
export type ContextCompactionRunner = (
|
|
92
|
+
params: ContextCompactionRunnerParams,
|
|
93
|
+
) => Effect.Effect<CompactionOutput, unknown>
|
|
84
94
|
|
|
85
95
|
export interface CreateContextCompactionRuntimeOptions {
|
|
86
96
|
runCompacter: ContextCompactionRunner
|
|
@@ -104,7 +114,7 @@ export interface ContextCompactionRuntime {
|
|
|
104
114
|
liveMessages: ChatMessage[]
|
|
105
115
|
contextSize?: number
|
|
106
116
|
}) => CompactionAssessment
|
|
107
|
-
compactHistory: (params: CompactHistoryParams) =>
|
|
117
|
+
compactHistory: (params: CompactHistoryParams) => Effect.Effect<CompactHistoryResult, CompactionError>
|
|
108
118
|
}
|
|
109
119
|
|
|
110
120
|
function estimateTokens(text: string): number {
|
|
@@ -325,22 +335,32 @@ export function createContextCompactionRuntime(
|
|
|
325
335
|
return { estimatedTokens, threshold, shouldCompact: estimatedTokens >= threshold }
|
|
326
336
|
}
|
|
327
337
|
|
|
328
|
-
const compactContextMessagesEffect = (params: {
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
338
|
+
const compactContextMessagesEffect = Effect.fn('ContextCompaction.compactContextMessages')(function* (params: {
|
|
339
|
+
previousSummary: string
|
|
340
|
+
newMessages: ContextMessage[]
|
|
341
|
+
}) {
|
|
342
|
+
const chunks = splitByCharBudget(params.newMessages, compactionChunkMaxChars)
|
|
343
|
+
const initialSummary = normalizeSummary(params.previousSummary)
|
|
344
|
+
|
|
345
|
+
const finalSummary = yield* iterateEffect<{ summary: string; index: number }, CompactionError, never>(
|
|
346
|
+
{ summary: initialSummary, index: 0 },
|
|
347
|
+
{
|
|
348
|
+
while: (state) => state.index < chunks.length,
|
|
349
|
+
body: (state) =>
|
|
350
|
+
Effect.gen(function* () {
|
|
351
|
+
const chunk = chunks[state.index]
|
|
352
|
+
const transcript = toCompactionTranscript(chunk)
|
|
353
|
+
const output = yield* options.runCompacter({ previousSummary: state.summary, chunk, transcript }).pipe(
|
|
354
|
+
Effect.mapError((error) => new CompactionError({ message: String(error), cause: error })),
|
|
355
|
+
Effect.retry(COMPACTION_RUNNER_RETRY_OPTIONS),
|
|
356
|
+
)
|
|
357
|
+
return { summary: normalizeSummary(output.summary), index: state.index + 1 }
|
|
358
|
+
}),
|
|
359
|
+
},
|
|
360
|
+
)
|
|
361
|
+
|
|
362
|
+
return { summary: finalSummary.summary }
|
|
363
|
+
})
|
|
344
364
|
|
|
345
365
|
const rollupSummaryIfOversizedEffect = (summary: string) =>
|
|
346
366
|
Effect.gen(function* () {
|
|
@@ -356,81 +376,104 @@ export function createContextCompactionRuntime(
|
|
|
356
376
|
return normalizeSummary(output.summary)
|
|
357
377
|
})
|
|
358
378
|
|
|
379
|
+
type CompactionLoopState = {
|
|
380
|
+
summaryText: string
|
|
381
|
+
remainingMessages: ChatMessage[]
|
|
382
|
+
compactedMessages: ChatMessage[]
|
|
383
|
+
lastCompactedMessageId: string | undefined
|
|
384
|
+
estimatedTokens: number
|
|
385
|
+
done: boolean
|
|
386
|
+
}
|
|
387
|
+
|
|
359
388
|
const compactHistoryEffect = (params: CompactHistoryParams) =>
|
|
360
389
|
Effect.gen(function* () {
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
const summaryPayload = buildSyntheticSummaryPayload(summaryText)
|
|
366
|
-
const initialPayload = stringifyUnknown([...(summaryPayload ? [summaryPayload] : []), ...remainingMessages]) ?? ''
|
|
390
|
+
const initialSummaryText = normalizeSummary(params.summaryText)
|
|
391
|
+
const initialRemaining = [...params.liveMessages]
|
|
392
|
+
const summaryPayload = buildSyntheticSummaryPayload(initialSummaryText)
|
|
393
|
+
const initialPayload = stringifyUnknown([...(summaryPayload ? [summaryPayload] : []), ...initialRemaining]) ?? ''
|
|
367
394
|
const inputChars = initialPayload.length
|
|
368
395
|
|
|
369
|
-
const
|
|
370
|
-
const exitSummaryPayload = buildSyntheticSummaryPayload(summaryText)
|
|
396
|
+
const buildExitResult = (state: CompactionLoopState): CompactHistoryResult => {
|
|
397
|
+
const exitSummaryPayload = buildSyntheticSummaryPayload(state.summaryText)
|
|
371
398
|
const outputPayload =
|
|
372
|
-
stringifyUnknown([...(exitSummaryPayload ? [exitSummaryPayload] : []), ...remainingMessages]) ?? ''
|
|
399
|
+
stringifyUnknown([...(exitSummaryPayload ? [exitSummaryPayload] : []), ...state.remainingMessages]) ?? ''
|
|
373
400
|
return {
|
|
374
|
-
compacted: compactedMessages.length > 0,
|
|
375
|
-
summaryText,
|
|
376
|
-
...(lastCompactedMessageId ? { lastCompactedMessageId } : {}),
|
|
377
|
-
compactedMessages,
|
|
378
|
-
compactedMessageCount: compactedMessages.length,
|
|
379
|
-
remainingMessageCount: remainingMessages.length,
|
|
380
|
-
estimatedTokens,
|
|
401
|
+
compacted: state.compactedMessages.length > 0,
|
|
402
|
+
summaryText: state.summaryText,
|
|
403
|
+
...(state.lastCompactedMessageId ? { lastCompactedMessageId: state.lastCompactedMessageId } : {}),
|
|
404
|
+
compactedMessages: state.compactedMessages,
|
|
405
|
+
compactedMessageCount: state.compactedMessages.length,
|
|
406
|
+
remainingMessageCount: state.remainingMessages.length,
|
|
407
|
+
estimatedTokens: state.estimatedTokens,
|
|
381
408
|
inputChars,
|
|
382
409
|
outputChars: outputPayload.length,
|
|
383
410
|
}
|
|
384
411
|
}
|
|
385
412
|
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
return buildEarlyExitResult(assessment.estimatedTokens)
|
|
395
|
-
}
|
|
396
|
-
|
|
397
|
-
const boundary = Math.max(0, remainingMessages.length - params.tailMessageCount)
|
|
398
|
-
if (boundary <= 0) {
|
|
399
|
-
return buildEarlyExitResult(assessment.estimatedTokens)
|
|
400
|
-
}
|
|
401
|
-
|
|
402
|
-
const candidatePrefix = remainingMessages.slice(0, boundary)
|
|
403
|
-
const messagesToCompact = candidatePrefix.filter((message) => !readIsCompacted(message))
|
|
404
|
-
const contextMessages = messagesToCompact
|
|
405
|
-
.map(toContextMessageFromChatMessage)
|
|
406
|
-
.filter((message) => compactWhitespace(message.text).length > 0)
|
|
407
|
-
const sourceText = toCompactionTranscript(contextMessages)
|
|
408
|
-
|
|
409
|
-
if (!compactWhitespace(sourceText)) {
|
|
410
|
-
return buildEarlyExitResult(assessment.estimatedTokens)
|
|
411
|
-
}
|
|
412
|
-
|
|
413
|
-
let nextSummary = normalizeSummary(
|
|
414
|
-
(yield* compactContextMessagesEffect({ previousSummary: summaryText, newMessages: contextMessages })).summary,
|
|
415
|
-
)
|
|
416
|
-
nextSummary = yield* rollupSummaryIfOversizedEffect(nextSummary)
|
|
417
|
-
|
|
418
|
-
if (nextSummary.length >= sourceText.length) {
|
|
419
|
-
return yield* new CompactionError({ message: 'Compaction summary is not shorter than compacted source' })
|
|
420
|
-
}
|
|
413
|
+
const initialState: CompactionLoopState = {
|
|
414
|
+
summaryText: initialSummaryText,
|
|
415
|
+
remainingMessages: initialRemaining,
|
|
416
|
+
compactedMessages: [],
|
|
417
|
+
lastCompactedMessageId: undefined,
|
|
418
|
+
estimatedTokens: 0,
|
|
419
|
+
done: false,
|
|
420
|
+
}
|
|
421
421
|
|
|
422
|
-
|
|
423
|
-
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
|
|
428
|
-
|
|
422
|
+
const finalState = yield* iterateEffect<CompactionLoopState, CompactionError, never>(initialState, {
|
|
423
|
+
while: (state) => !state.done,
|
|
424
|
+
body: (state) =>
|
|
425
|
+
Effect.gen(function* () {
|
|
426
|
+
const assessment = shouldCompactHistory({
|
|
427
|
+
summaryText: state.summaryText,
|
|
428
|
+
liveMessages: state.remainingMessages,
|
|
429
|
+
contextSize: params.contextSize,
|
|
430
|
+
})
|
|
431
|
+
|
|
432
|
+
if (!assessment.shouldCompact) {
|
|
433
|
+
return { ...state, estimatedTokens: assessment.estimatedTokens, done: true }
|
|
434
|
+
}
|
|
435
|
+
|
|
436
|
+
const boundary = Math.max(0, state.remainingMessages.length - params.tailMessageCount)
|
|
437
|
+
if (boundary <= 0) {
|
|
438
|
+
return { ...state, estimatedTokens: assessment.estimatedTokens, done: true }
|
|
439
|
+
}
|
|
440
|
+
|
|
441
|
+
const candidatePrefix = state.remainingMessages.slice(0, boundary)
|
|
442
|
+
const messagesToCompact = candidatePrefix.filter((message) => !readIsCompacted(message))
|
|
443
|
+
const contextMessages = messagesToCompact
|
|
444
|
+
.map(toContextMessageFromChatMessage)
|
|
445
|
+
.filter((message) => compactWhitespace(message.text).length > 0)
|
|
446
|
+
const sourceText = toCompactionTranscript(contextMessages)
|
|
447
|
+
|
|
448
|
+
if (!compactWhitespace(sourceText)) {
|
|
449
|
+
return { ...state, estimatedTokens: assessment.estimatedTokens, done: true }
|
|
450
|
+
}
|
|
451
|
+
|
|
452
|
+
const compacted = yield* compactContextMessagesEffect({
|
|
453
|
+
previousSummary: state.summaryText,
|
|
454
|
+
newMessages: contextMessages,
|
|
455
|
+
})
|
|
456
|
+
const rolledSummary = yield* rollupSummaryIfOversizedEffect(normalizeSummary(compacted.summary))
|
|
457
|
+
|
|
458
|
+
if (rolledSummary.length >= sourceText.length) {
|
|
459
|
+
return yield* new CompactionError({ message: 'Compaction summary is not shorter than compacted source' })
|
|
460
|
+
}
|
|
461
|
+
|
|
462
|
+
return {
|
|
463
|
+
summaryText: rolledSummary,
|
|
464
|
+
remainingMessages: state.remainingMessages.slice(boundary),
|
|
465
|
+
compactedMessages: [
|
|
466
|
+
...state.compactedMessages,
|
|
467
|
+
...candidatePrefix.map((message) => markMessageCompacted(message, now)),
|
|
468
|
+
],
|
|
469
|
+
lastCompactedMessageId: candidatePrefix.at(-1)?.id ?? state.lastCompactedMessageId,
|
|
470
|
+
estimatedTokens: assessment.estimatedTokens,
|
|
471
|
+
done: false,
|
|
472
|
+
}
|
|
473
|
+
}),
|
|
474
|
+
})
|
|
429
475
|
|
|
430
|
-
|
|
431
|
-
continue
|
|
432
|
-
}
|
|
433
|
-
}
|
|
476
|
+
return buildExitResult(finalState)
|
|
434
477
|
})
|
|
435
478
|
|
|
436
479
|
return {
|
|
@@ -438,11 +481,14 @@ export function createContextCompactionRuntime(
|
|
|
438
481
|
prependSummaryMessage,
|
|
439
482
|
estimateThreshold,
|
|
440
483
|
shouldCompactHistory,
|
|
441
|
-
compactHistory:
|
|
484
|
+
compactHistory: compactHistoryEffect,
|
|
442
485
|
}
|
|
443
486
|
}
|
|
444
487
|
|
|
445
|
-
export function parseCompactionOutput(value: unknown): CompactionOutput {
|
|
446
|
-
const parsed = ContextCompactionOutputSchema.
|
|
447
|
-
|
|
488
|
+
export function parseCompactionOutput(value: unknown): Effect.Effect<CompactionOutput, CompactionParseError> {
|
|
489
|
+
const parsed = ContextCompactionOutputSchema.safeParse(value)
|
|
490
|
+
if (!parsed.success) {
|
|
491
|
+
return Effect.fail(new CompactionParseError({ message: 'Failed to parse compaction output', cause: parsed.error }))
|
|
492
|
+
}
|
|
493
|
+
return Effect.succeed({ summary: parsed.data.summary })
|
|
448
494
|
}
|
|
@@ -0,0 +1,203 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Builds the domain-service Layer tree for `createLotaRuntime`.
|
|
3
|
+
*
|
|
4
|
+
* The services form a 9-tier dependency graph on top of the infrastructure
|
|
5
|
+
* layer (config, logging, database, redis, agents, threads, extensions).
|
|
6
|
+
* Each tier is provided with the accumulated context of earlier tiers so
|
|
7
|
+
* every service resolves cleanly when the ManagedRuntime eagerly loads them.
|
|
8
|
+
*/
|
|
9
|
+
|
|
10
|
+
import type { Layer as LayerType } from 'effect'
|
|
11
|
+
import { Layer } from 'effect'
|
|
12
|
+
|
|
13
|
+
import { AiGatewayLive } from '../ai-gateway/ai-gateway'
|
|
14
|
+
import { EmbeddingCacheLive } from '../ai/embedding-cache'
|
|
15
|
+
import type { buildInfrastructureLayer } from '../effect/layers'
|
|
16
|
+
import { LotaQueuesLive } from '../queues/queues.service'
|
|
17
|
+
import { SharedThreadStreamSubscriberLive } from '../redis/stream-context'
|
|
18
|
+
import { AgentActivityServiceLive } from '../services/agent-activity.service'
|
|
19
|
+
import { AgentExecutorServiceLive } from '../services/agent-executor.service'
|
|
20
|
+
import { ArtifactServiceLive } from '../services/artifact.service'
|
|
21
|
+
import { AttachmentServiceLive } from '../services/attachment.service'
|
|
22
|
+
import { AutonomousJobServiceLive } from '../services/autonomous-job.service'
|
|
23
|
+
import { BackgroundWorkServiceLive } from '../services/background-work.service'
|
|
24
|
+
import { ChatRunRegistryLive } from '../services/chat-run-registry.service'
|
|
25
|
+
import { ContextCompactionServiceLive } from '../services/context-compaction.service'
|
|
26
|
+
import { DocumentChunkServiceLive } from '../services/document-chunk.service'
|
|
27
|
+
import { ExecutionPlanServiceLive } from '../services/execution-plan/execution-plan.service'
|
|
28
|
+
import { FeedbackLoopServiceLive } from '../services/feedback-loop.service'
|
|
29
|
+
import { GlobalOrchestratorServiceLive } from '../services/global-orchestrator.service'
|
|
30
|
+
import { InstitutionalMemoryServiceLive } from '../services/institutional-memory.service'
|
|
31
|
+
import { LearnedSkillServiceLive } from '../services/learned-skill.service'
|
|
32
|
+
import { MemoryServiceLive } from '../services/memory/memory.service'
|
|
33
|
+
import { RerankServiceLive } from '../services/memory/rerank.service'
|
|
34
|
+
import { MonitoringWindowServiceLive } from '../services/monitoring-window.service'
|
|
35
|
+
import { MutatingApprovalServiceLive } from '../services/mutating-approval.service'
|
|
36
|
+
import { NodeWorkspaceServiceLive } from '../services/node-workspace.service'
|
|
37
|
+
import { NotificationServiceLive } from '../services/notification.service'
|
|
38
|
+
import { OrganizationMemberServiceLive } from '../services/organization-member.service'
|
|
39
|
+
import { OrganizationServiceLive } from '../services/organization.service'
|
|
40
|
+
import { OwnershipDispatcherServiceLive } from '../services/ownership-dispatcher.service'
|
|
41
|
+
import { PlanAgentHeartbeatServiceLive } from '../services/plan/plan-agent-heartbeat.service'
|
|
42
|
+
import { PlanAgentQueryServiceLive } from '../services/plan/plan-agent-query.service'
|
|
43
|
+
import { PlanApprovalServiceLive } from '../services/plan/plan-approval.service'
|
|
44
|
+
import { PlanArtifactServiceLive } from '../services/plan/plan-artifact.service'
|
|
45
|
+
import { PlanBuilderServiceLive } from '../services/plan/plan-builder.service'
|
|
46
|
+
import { PlanCheckpointServiceLive } from '../services/plan/plan-checkpoint.service'
|
|
47
|
+
import { PlanCompilerServiceLive } from '../services/plan/plan-compiler.service'
|
|
48
|
+
import { PlanCoordinationServiceLive } from '../services/plan/plan-coordination.service'
|
|
49
|
+
import { PlanCycleServiceLive } from '../services/plan/plan-cycle.service'
|
|
50
|
+
import { PlanDeadlineServiceLive } from '../services/plan/plan-deadline.service'
|
|
51
|
+
import { PlanEventDeliveryServiceLive } from '../services/plan/plan-event-delivery.service'
|
|
52
|
+
import { PlanExecutorServiceLive } from '../services/plan/plan-executor.service'
|
|
53
|
+
import { PlanRunServiceLive } from '../services/plan/plan-run.service'
|
|
54
|
+
import { PlanSchedulerServiceLive } from '../services/plan/plan-scheduler.service'
|
|
55
|
+
import { PlanTemplateServiceLive } from '../services/plan/plan-template.service'
|
|
56
|
+
import { PlanValidatorServiceLive } from '../services/plan/plan-validator.service'
|
|
57
|
+
import { PlanWorkspaceServiceLive } from '../services/plan/plan-workspace.service'
|
|
58
|
+
import { PluginExecutorServiceLive } from '../services/plugin-executor.service'
|
|
59
|
+
import { QualityMetricsServiceLive } from '../services/quality-metrics.service'
|
|
60
|
+
import { QueueJobServiceLive } from '../services/queue-job.service'
|
|
61
|
+
import { RecentActivityTitleServiceLive } from '../services/recent-activity-title.service'
|
|
62
|
+
import { RecentActivityServiceLive } from '../services/recent-activity.service'
|
|
63
|
+
import { SkillResolverServiceLive } from '../services/skill-resolver.service'
|
|
64
|
+
import { SocialChatHistoryServiceLive } from '../services/social-chat-history.service'
|
|
65
|
+
import { SystemExecutorServiceLive } from '../services/system-executor.service'
|
|
66
|
+
import { ThreadMessageServiceLive } from '../services/thread/thread-message.service'
|
|
67
|
+
import { ThreadTitleServiceLive } from '../services/thread/thread-title.service'
|
|
68
|
+
import { ThreadTurnServiceLive } from '../services/thread/thread-turn'
|
|
69
|
+
import { ThreadTurnPreparationServiceLive } from '../services/thread/thread-turn-preparation.service'
|
|
70
|
+
import { ThreadServiceLive } from '../services/thread/thread.service'
|
|
71
|
+
import { UserServiceLive } from '../services/user.service'
|
|
72
|
+
import { WriteIntentValidatorServiceLive } from '../services/write-intent-validator.service'
|
|
73
|
+
import { AttachmentStorageServiceLive } from '../storage/attachment-storage.service'
|
|
74
|
+
import { GeneratedDocumentStorageServiceLive } from '../storage/generated-document-storage.service'
|
|
75
|
+
import { FirecrawlLive } from '../tools/firecrawl-client'
|
|
76
|
+
import { CompactionCoordinationLive } from './chat-run-orchestration'
|
|
77
|
+
import { HelperModelLive } from './helper-model'
|
|
78
|
+
|
|
79
|
+
function provide<A, E, R extends RCtx, RCtx, E2>(
|
|
80
|
+
layer: LayerType.Layer<A, E, R>,
|
|
81
|
+
ctx: LayerType.Layer<RCtx, E2, never>,
|
|
82
|
+
): LayerType.Layer<A, E | E2, never> {
|
|
83
|
+
return Layer.provideMerge(ctx)(layer)
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
type InfrastructureLayer = ReturnType<typeof buildInfrastructureLayer>
|
|
87
|
+
|
|
88
|
+
/**
|
|
89
|
+
* Compose the domain service layer tree on top of the supplied infrastructure
|
|
90
|
+
* layer. The returned layer has no remaining requirements and can be fed
|
|
91
|
+
* straight into `ManagedRuntime.make`.
|
|
92
|
+
*/
|
|
93
|
+
export function buildDomainServiceLayer(infrastructureLayer: InfrastructureLayer) {
|
|
94
|
+
const tier0 = provide(
|
|
95
|
+
Layer.mergeAll(
|
|
96
|
+
BackgroundWorkServiceLive,
|
|
97
|
+
ChatRunRegistryLive,
|
|
98
|
+
CompactionCoordinationLive,
|
|
99
|
+
DocumentChunkServiceLive,
|
|
100
|
+
NodeWorkspaceServiceLive,
|
|
101
|
+
NotificationServiceLive,
|
|
102
|
+
PlanArtifactServiceLive,
|
|
103
|
+
PlanBuilderServiceLive,
|
|
104
|
+
WriteIntentValidatorServiceLive,
|
|
105
|
+
),
|
|
106
|
+
infrastructureLayer,
|
|
107
|
+
)
|
|
108
|
+
const ctx0 = Layer.mergeAll(
|
|
109
|
+
infrastructureLayer,
|
|
110
|
+
provide(Layer.mergeAll(AiGatewayLive, EmbeddingCacheLive, FirecrawlLive, HelperModelLive), infrastructureLayer),
|
|
111
|
+
tier0,
|
|
112
|
+
)
|
|
113
|
+
|
|
114
|
+
const tier1 = provide(
|
|
115
|
+
Layer.mergeAll(
|
|
116
|
+
SharedThreadStreamSubscriberLive,
|
|
117
|
+
AgentExecutorServiceLive,
|
|
118
|
+
AttachmentStorageServiceLive,
|
|
119
|
+
GeneratedDocumentStorageServiceLive,
|
|
120
|
+
LearnedSkillServiceLive,
|
|
121
|
+
OrganizationServiceLive,
|
|
122
|
+
OrganizationMemberServiceLive,
|
|
123
|
+
PlanApprovalServiceLive,
|
|
124
|
+
PlanRunServiceLive,
|
|
125
|
+
PlanWorkspaceServiceLive,
|
|
126
|
+
PluginExecutorServiceLive,
|
|
127
|
+
QualityMetricsServiceLive,
|
|
128
|
+
QueueJobServiceLive,
|
|
129
|
+
RecentActivityServiceLive,
|
|
130
|
+
RerankServiceLive,
|
|
131
|
+
SocialChatHistoryServiceLive,
|
|
132
|
+
SystemExecutorServiceLive,
|
|
133
|
+
ThreadMessageServiceLive,
|
|
134
|
+
UserServiceLive,
|
|
135
|
+
),
|
|
136
|
+
ctx0,
|
|
137
|
+
)
|
|
138
|
+
const ctx1Base = Layer.mergeAll(ctx0, tier1)
|
|
139
|
+
|
|
140
|
+
// LotaQueuesLive depends only on Redis + QueueJobService from tier1/infra.
|
|
141
|
+
// It's threaded in before the tiers that need queue enqueue access so the
|
|
142
|
+
// service layers that enqueue jobs (AutonomousJobService, plan scheduler,
|
|
143
|
+
// heartbeat, etc.) can resolve LotaQueuesServiceTag cleanly.
|
|
144
|
+
const queuesTier = provide(LotaQueuesLive, ctx1Base)
|
|
145
|
+
const ctx1 = Layer.mergeAll(ctx1Base, queuesTier)
|
|
146
|
+
// PlanSchedulerServiceLive previously sat in tier1; it now depends on the
|
|
147
|
+
// queue layer, so it moves to the merged ctx1 context with queues available.
|
|
148
|
+
const planSchedulerTier = provide(PlanSchedulerServiceLive, ctx1)
|
|
149
|
+
const ctx1WithScheduler = Layer.mergeAll(ctx1, planSchedulerTier)
|
|
150
|
+
|
|
151
|
+
const tier2 = provide(
|
|
152
|
+
Layer.mergeAll(
|
|
153
|
+
ArtifactServiceLive,
|
|
154
|
+
AttachmentServiceLive,
|
|
155
|
+
ContextCompactionServiceLive,
|
|
156
|
+
FeedbackLoopServiceLive,
|
|
157
|
+
InstitutionalMemoryServiceLive,
|
|
158
|
+
MemoryServiceLive,
|
|
159
|
+
MonitoringWindowServiceLive,
|
|
160
|
+
MutatingApprovalServiceLive,
|
|
161
|
+
PlanAgentQueryServiceLive,
|
|
162
|
+
PlanCheckpointServiceLive,
|
|
163
|
+
PlanCoordinationServiceLive,
|
|
164
|
+
PlanEventDeliveryServiceLive,
|
|
165
|
+
SkillResolverServiceLive,
|
|
166
|
+
RecentActivityTitleServiceLive,
|
|
167
|
+
),
|
|
168
|
+
ctx1WithScheduler,
|
|
169
|
+
)
|
|
170
|
+
const ctx2 = Layer.mergeAll(ctx1WithScheduler, tier2)
|
|
171
|
+
|
|
172
|
+
const tier3 = provide(Layer.mergeAll(PlanValidatorServiceLive, ThreadServiceLive), ctx2)
|
|
173
|
+
const ctx3 = Layer.mergeAll(ctx2, tier3)
|
|
174
|
+
|
|
175
|
+
const tier4 = provide(Layer.mergeAll(PlanCompilerServiceLive, ThreadTitleServiceLive), ctx3)
|
|
176
|
+
const ctx4 = Layer.mergeAll(ctx3, tier4)
|
|
177
|
+
|
|
178
|
+
const tier5 = provide(PlanExecutorServiceLive, ctx4)
|
|
179
|
+
const ctx5 = Layer.mergeAll(ctx4, tier5)
|
|
180
|
+
|
|
181
|
+
const tier6 = provide(
|
|
182
|
+
Layer.mergeAll(OwnershipDispatcherServiceLive, PlanAgentHeartbeatServiceLive, PlanDeadlineServiceLive),
|
|
183
|
+
ctx5,
|
|
184
|
+
)
|
|
185
|
+
const ctx6 = Layer.mergeAll(ctx5, tier6)
|
|
186
|
+
|
|
187
|
+
const tier7 = provide(Layer.mergeAll(ExecutionPlanServiceLive, GlobalOrchestratorServiceLive), ctx6)
|
|
188
|
+
const ctx7 = Layer.mergeAll(ctx6, tier7)
|
|
189
|
+
|
|
190
|
+
const tier8 = provide(
|
|
191
|
+
Layer.mergeAll(
|
|
192
|
+
PlanTemplateServiceLive,
|
|
193
|
+
AutonomousJobServiceLive,
|
|
194
|
+
AgentActivityServiceLive,
|
|
195
|
+
ThreadTurnPreparationServiceLive,
|
|
196
|
+
),
|
|
197
|
+
ctx7,
|
|
198
|
+
)
|
|
199
|
+
const ctx8 = Layer.mergeAll(ctx7, tier8)
|
|
200
|
+
|
|
201
|
+
const tier9 = provide(Layer.mergeAll(PlanCycleServiceLive, ThreadTurnServiceLive), ctx8)
|
|
202
|
+
return Layer.mergeAll(ctx8, tier9)
|
|
203
|
+
}
|