@bryti/agent 0.0.1 → 0.1.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/Dockerfile +27 -0
- package/README.md +77 -50
- package/config.example.yml +265 -0
- package/dist/active-hours.d.ts +23 -0
- package/dist/active-hours.d.ts.map +1 -0
- package/dist/active-hours.js +68 -0
- package/dist/active-hours.js.map +1 -0
- package/dist/agent.d.ts +84 -0
- package/dist/agent.d.ts.map +1 -0
- package/dist/agent.js +383 -0
- package/dist/agent.js.map +1 -0
- package/dist/channels/markdown/ir.d.ts +79 -0
- package/dist/channels/markdown/ir.d.ts.map +1 -0
- package/dist/channels/markdown/ir.js +824 -0
- package/dist/channels/markdown/ir.js.map +1 -0
- package/dist/channels/markdown/render.d.ts +35 -0
- package/dist/channels/markdown/render.d.ts.map +1 -0
- package/dist/channels/markdown/render.js +178 -0
- package/dist/channels/markdown/render.js.map +1 -0
- package/dist/channels/telegram-network-errors.d.ts +27 -0
- package/dist/channels/telegram-network-errors.d.ts.map +1 -0
- package/dist/channels/telegram-network-errors.js +156 -0
- package/dist/channels/telegram-network-errors.js.map +1 -0
- package/dist/channels/telegram.d.ts +76 -0
- package/dist/channels/telegram.d.ts.map +1 -0
- package/dist/channels/telegram.js +814 -0
- package/dist/channels/telegram.js.map +1 -0
- package/dist/channels/types.d.ts +59 -0
- package/dist/channels/types.d.ts.map +1 -0
- package/dist/channels/types.js +9 -0
- package/dist/channels/types.js.map +1 -0
- package/dist/channels/whatsapp.d.ts +45 -0
- package/dist/channels/whatsapp.d.ts.map +1 -0
- package/dist/channels/whatsapp.js +310 -0
- package/dist/channels/whatsapp.js.map +1 -0
- package/dist/cli.d.ts +13 -0
- package/dist/cli.d.ts.map +1 -0
- package/dist/cli.js +635 -0
- package/dist/cli.js.map +1 -0
- package/dist/commands.d.ts +35 -0
- package/dist/commands.d.ts.map +1 -0
- package/dist/commands.js +113 -0
- package/dist/commands.js.map +1 -0
- package/dist/compaction/history.d.ts +17 -0
- package/dist/compaction/history.d.ts.map +1 -0
- package/dist/compaction/history.js +35 -0
- package/dist/compaction/history.js.map +1 -0
- package/dist/compaction/index.d.ts +3 -0
- package/dist/compaction/index.d.ts.map +1 -0
- package/dist/compaction/index.js +3 -0
- package/dist/compaction/index.js.map +1 -0
- package/dist/compaction/proactive.d.ts +25 -0
- package/dist/compaction/proactive.d.ts.map +1 -0
- package/dist/compaction/proactive.js +87 -0
- package/dist/compaction/proactive.js.map +1 -0
- package/dist/compaction/transcript-repair.d.ts +55 -0
- package/dist/compaction/transcript-repair.d.ts.map +1 -0
- package/dist/compaction/transcript-repair.js +215 -0
- package/dist/compaction/transcript-repair.js.map +1 -0
- package/dist/config.d.ts +128 -0
- package/dist/config.d.ts.map +1 -0
- package/dist/config.js +317 -0
- package/dist/config.js.map +1 -0
- package/dist/crash-recovery.d.ts +23 -0
- package/dist/crash-recovery.d.ts.map +1 -0
- package/dist/crash-recovery.js +96 -0
- package/dist/crash-recovery.js.map +1 -0
- package/dist/defaults/extensions/EXTENSIONS.md +158 -0
- package/dist/defaults/extensions/documents-hedgedoc.ts +153 -0
- package/dist/history.d.ts +31 -0
- package/dist/history.d.ts.map +1 -0
- package/dist/history.js +49 -0
- package/dist/history.js.map +1 -0
- package/dist/index.d.ts +19 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +673 -0
- package/dist/index.js.map +1 -0
- package/dist/logger.d.ts +39 -0
- package/dist/logger.d.ts.map +1 -0
- package/dist/logger.js +143 -0
- package/dist/logger.js.map +1 -0
- package/dist/memory/conversation-search.d.ts +15 -0
- package/dist/memory/conversation-search.d.ts.map +1 -0
- package/dist/memory/conversation-search.js +60 -0
- package/dist/memory/conversation-search.js.map +1 -0
- package/dist/memory/core-memory.d.ts +28 -0
- package/dist/memory/core-memory.d.ts.map +1 -0
- package/dist/memory/core-memory.js +102 -0
- package/dist/memory/core-memory.js.map +1 -0
- package/dist/memory/embeddings.d.ts +44 -0
- package/dist/memory/embeddings.d.ts.map +1 -0
- package/dist/memory/embeddings.js +139 -0
- package/dist/memory/embeddings.js.map +1 -0
- package/dist/memory/search.d.ts +49 -0
- package/dist/memory/search.d.ts.map +1 -0
- package/dist/memory/search.js +97 -0
- package/dist/memory/search.js.map +1 -0
- package/dist/memory/store.d.ts +32 -0
- package/dist/memory/store.d.ts.map +1 -0
- package/dist/memory/store.js +205 -0
- package/dist/memory/store.js.map +1 -0
- package/dist/message-queue.d.ts +73 -0
- package/dist/message-queue.d.ts.map +1 -0
- package/dist/message-queue.js +188 -0
- package/dist/message-queue.js.map +1 -0
- package/dist/model-infra.d.ts +64 -0
- package/dist/model-infra.d.ts.map +1 -0
- package/dist/model-infra.js +202 -0
- package/dist/model-infra.js.map +1 -0
- package/dist/projection/format.d.ts +10 -0
- package/dist/projection/format.d.ts.map +1 -0
- package/dist/projection/format.js +30 -0
- package/dist/projection/format.js.map +1 -0
- package/dist/projection/index.d.ts +11 -0
- package/dist/projection/index.d.ts.map +1 -0
- package/dist/projection/index.js +9 -0
- package/dist/projection/index.js.map +1 -0
- package/dist/projection/reflection.d.ts +94 -0
- package/dist/projection/reflection.d.ts.map +1 -0
- package/dist/projection/reflection.js +334 -0
- package/dist/projection/reflection.js.map +1 -0
- package/dist/projection/store.d.ts +144 -0
- package/dist/projection/store.d.ts.map +1 -0
- package/dist/projection/store.js +519 -0
- package/dist/projection/store.js.map +1 -0
- package/dist/projection/tools.d.ts +11 -0
- package/dist/projection/tools.d.ts.map +1 -0
- package/dist/projection/tools.js +237 -0
- package/dist/projection/tools.js.map +1 -0
- package/dist/scheduler.d.ts +36 -0
- package/dist/scheduler.d.ts.map +1 -0
- package/dist/scheduler.js +286 -0
- package/dist/scheduler.js.map +1 -0
- package/dist/system-prompt.d.ts +41 -0
- package/dist/system-prompt.d.ts.map +1 -0
- package/dist/system-prompt.js +162 -0
- package/dist/system-prompt.js.map +1 -0
- package/dist/time.d.ts +52 -0
- package/dist/time.d.ts.map +1 -0
- package/dist/time.js +138 -0
- package/dist/time.js.map +1 -0
- package/dist/tools/archival-memory-tool.d.ts +8 -0
- package/dist/tools/archival-memory-tool.d.ts.map +1 -0
- package/dist/tools/archival-memory-tool.js +68 -0
- package/dist/tools/archival-memory-tool.js.map +1 -0
- package/dist/tools/conversation-search-tool.d.ts +6 -0
- package/dist/tools/conversation-search-tool.d.ts.map +1 -0
- package/dist/tools/conversation-search-tool.js +28 -0
- package/dist/tools/conversation-search-tool.js.map +1 -0
- package/dist/tools/core-memory-tool.d.ts +7 -0
- package/dist/tools/core-memory-tool.d.ts.map +1 -0
- package/dist/tools/core-memory-tool.js +59 -0
- package/dist/tools/core-memory-tool.js.map +1 -0
- package/dist/tools/fetch-url.d.ts +15 -0
- package/dist/tools/fetch-url.d.ts.map +1 -0
- package/dist/tools/fetch-url.js +76 -0
- package/dist/tools/fetch-url.js.map +1 -0
- package/dist/tools/files.d.ts +10 -0
- package/dist/tools/files.d.ts.map +1 -0
- package/dist/tools/files.js +127 -0
- package/dist/tools/files.js.map +1 -0
- package/dist/tools/index.d.ts +17 -0
- package/dist/tools/index.d.ts.map +1 -0
- package/dist/tools/index.js +118 -0
- package/dist/tools/index.js.map +1 -0
- package/dist/tools/result.d.ts +21 -0
- package/dist/tools/result.d.ts.map +1 -0
- package/dist/tools/result.js +36 -0
- package/dist/tools/result.js.map +1 -0
- package/dist/tools/skill-install.d.ts +17 -0
- package/dist/tools/skill-install.d.ts.map +1 -0
- package/dist/tools/skill-install.js +148 -0
- package/dist/tools/skill-install.js.map +1 -0
- package/dist/tools/web-search.d.ts +42 -0
- package/dist/tools/web-search.d.ts.map +1 -0
- package/dist/tools/web-search.js +237 -0
- package/dist/tools/web-search.js.map +1 -0
- package/dist/trust/guardrail.d.ts +60 -0
- package/dist/trust/guardrail.d.ts.map +1 -0
- package/dist/trust/guardrail.js +171 -0
- package/dist/trust/guardrail.js.map +1 -0
- package/dist/trust/index.d.ts +12 -0
- package/dist/trust/index.d.ts.map +1 -0
- package/dist/trust/index.js +12 -0
- package/dist/trust/index.js.map +1 -0
- package/dist/trust/store.d.ts +118 -0
- package/dist/trust/store.d.ts.map +1 -0
- package/dist/trust/store.js +209 -0
- package/dist/trust/store.js.map +1 -0
- package/dist/trust/wrapper.d.ts +36 -0
- package/dist/trust/wrapper.d.ts.map +1 -0
- package/dist/trust/wrapper.js +142 -0
- package/dist/trust/wrapper.js.map +1 -0
- package/dist/usage.d.ts +53 -0
- package/dist/usage.d.ts.map +1 -0
- package/dist/usage.js +124 -0
- package/dist/usage.js.map +1 -0
- package/dist/util/math.d.ts +9 -0
- package/dist/util/math.d.ts.map +1 -0
- package/dist/util/math.js +22 -0
- package/dist/util/math.js.map +1 -0
- package/dist/util/ssrf.d.ts +21 -0
- package/dist/util/ssrf.d.ts.map +1 -0
- package/dist/util/ssrf.js +77 -0
- package/dist/util/ssrf.js.map +1 -0
- package/dist/workers/index.d.ts +8 -0
- package/dist/workers/index.d.ts.map +1 -0
- package/dist/workers/index.js +7 -0
- package/dist/workers/index.js.map +1 -0
- package/dist/workers/registry.d.ts +53 -0
- package/dist/workers/registry.d.ts.map +1 -0
- package/dist/workers/registry.js +38 -0
- package/dist/workers/registry.js.map +1 -0
- package/dist/workers/scoped-tools.d.ts +21 -0
- package/dist/workers/scoped-tools.d.ts.map +1 -0
- package/dist/workers/scoped-tools.js +111 -0
- package/dist/workers/scoped-tools.js.map +1 -0
- package/dist/workers/spawn.d.ts +62 -0
- package/dist/workers/spawn.d.ts.map +1 -0
- package/dist/workers/spawn.js +314 -0
- package/dist/workers/spawn.js.map +1 -0
- package/dist/workers/tools.d.ts +26 -0
- package/dist/workers/tools.d.ts.map +1 -0
- package/dist/workers/tools.js +380 -0
- package/dist/workers/tools.js.map +1 -0
- package/docker-compose.yml +72 -0
- package/package.json +16 -1
- package/run.sh +27 -0
|
@@ -0,0 +1,237 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Projection tools: create, list, resolve, and link projections.
|
|
3
|
+
*/
|
|
4
|
+
import { Type } from "@sinclair/typebox";
|
|
5
|
+
// ---------------------------------------------------------------------------
|
|
6
|
+
// Tool schemas
|
|
7
|
+
// ---------------------------------------------------------------------------
|
|
8
|
+
const projectSchema = Type.Object({
|
|
9
|
+
summary: Type.String({ description: "One-line description of the future event or expectation" }),
|
|
10
|
+
when: Type.Optional(Type.String({
|
|
11
|
+
description: "When this is expected to happen. Use a specific ISO datetime for exact events " +
|
|
12
|
+
"(e.g. '2026-02-19T10:00'). IMPORTANT: always express times in UTC. " +
|
|
13
|
+
"If the user said '13:45' in their local timezone, convert to UTC before storing. " +
|
|
14
|
+
"Use a date string for day-resolution (e.g. '2026-02-19'), " +
|
|
15
|
+
"'someday' for no specific time, or a natural phrase if UTC conversion is not possible.",
|
|
16
|
+
})),
|
|
17
|
+
resolution: Type.Optional(Type.Union([
|
|
18
|
+
Type.Literal("exact"),
|
|
19
|
+
Type.Literal("day"),
|
|
20
|
+
Type.Literal("week"),
|
|
21
|
+
Type.Literal("month"),
|
|
22
|
+
Type.Literal("someday"),
|
|
23
|
+
], { description: "Granularity of the time expression: exact | day | week | month | someday" })),
|
|
24
|
+
recurrence: Type.Optional(Type.String({
|
|
25
|
+
description: "Cron expression for repeating events. " +
|
|
26
|
+
"Use standard 5-field cron syntax (minute hour day month weekday). " +
|
|
27
|
+
"Examples: '0 9 * * 1' (every Monday at 09:00 UTC), '0 9 1 * *' (first of each month at 09:00 UTC), " +
|
|
28
|
+
"'0 9 * * 5' (every Friday at 09:00 UTC). " +
|
|
29
|
+
"Only set this for genuinely recurring events. Leave unset for one-off events.",
|
|
30
|
+
})),
|
|
31
|
+
trigger_on_fact: Type.Optional(Type.String({
|
|
32
|
+
description: "Keyword or short phrase that will activate this projection when a matching fact is archived. " +
|
|
33
|
+
"Use for 'when X happens, do Y' situations where X is an external event, not a time. " +
|
|
34
|
+
"Example: 'dentist confirmed' activates a projection when the user archives a fact containing those words. " +
|
|
35
|
+
"Keep it short and distinctive. Leave unset for time-driven projections.",
|
|
36
|
+
})),
|
|
37
|
+
context: Type.Optional(Type.String({
|
|
38
|
+
description: "Optional notes: related events, implications, what to watch for",
|
|
39
|
+
})),
|
|
40
|
+
linked_ids: Type.Optional(Type.Array(Type.String(), {
|
|
41
|
+
description: "IDs of related projections",
|
|
42
|
+
})),
|
|
43
|
+
depends_on: Type.Optional(Type.Array(Type.Object({
|
|
44
|
+
projection_id: Type.String({ description: "Projection id this new projection depends on" }),
|
|
45
|
+
condition: Type.String({ description: "Condition to satisfy (e.g. done, cancelled, or natural language)" }),
|
|
46
|
+
condition_type: Type.Optional(Type.Union([
|
|
47
|
+
Type.Literal("status_change"),
|
|
48
|
+
Type.Literal("llm"),
|
|
49
|
+
])),
|
|
50
|
+
}), {
|
|
51
|
+
description: "Optional dependency rules that must be met before this projection activates",
|
|
52
|
+
})),
|
|
53
|
+
});
|
|
54
|
+
const getProjectionsSchema = Type.Object({
|
|
55
|
+
horizon_days: Type.Optional(Type.Number({
|
|
56
|
+
description: "How many days ahead to look (default: 7). Always includes someday items.",
|
|
57
|
+
})),
|
|
58
|
+
});
|
|
59
|
+
const resolveProjectionSchema = Type.Object({
|
|
60
|
+
id: Type.String({ description: "Projection ID to resolve" }),
|
|
61
|
+
outcome: Type.Union([
|
|
62
|
+
Type.Literal("done"),
|
|
63
|
+
Type.Literal("cancelled"),
|
|
64
|
+
Type.Literal("passed"),
|
|
65
|
+
], { description: "How the projection resolved: done | cancelled | passed" }),
|
|
66
|
+
});
|
|
67
|
+
const linkProjectionSchema = Type.Object({
|
|
68
|
+
observer_id: Type.String({ description: "Projection that waits for a condition" }),
|
|
69
|
+
subject_id: Type.String({ description: "Projection being observed" }),
|
|
70
|
+
condition: Type.String({ description: "Condition to satisfy (e.g. done, cancelled, or natural language)" }),
|
|
71
|
+
condition_type: Type.Optional(Type.Union([
|
|
72
|
+
Type.Literal("status_change"),
|
|
73
|
+
Type.Literal("llm"),
|
|
74
|
+
])),
|
|
75
|
+
});
|
|
76
|
+
// ---------------------------------------------------------------------------
|
|
77
|
+
// Tool factory
|
|
78
|
+
// ---------------------------------------------------------------------------
|
|
79
|
+
/**
|
|
80
|
+
* Convert a naive local datetime to UTC ("YYYY-MM-DD HH:MM"). Strings with
|
|
81
|
+
* explicit offsets are normalized; no timezone means returned unchanged.
|
|
82
|
+
*/
|
|
83
|
+
function toUtcDatetime(naive, timezone) {
|
|
84
|
+
if (!timezone)
|
|
85
|
+
return naive.replace("T", " ");
|
|
86
|
+
// If it already carries offset info, just normalise separator and return
|
|
87
|
+
if (/[Z+\-]\d{2}:?\d{2}$/.test(naive) || naive.endsWith("Z")) {
|
|
88
|
+
return naive.replace("T", " ");
|
|
89
|
+
}
|
|
90
|
+
// Parse as local time in the given timezone using the Temporal-free approach:
|
|
91
|
+
// construct an ISO string with the timezone, let Date parse it via toLocaleString trick.
|
|
92
|
+
// We use the "sv-SE" locale which gives YYYY-MM-DD HH:MM:SS format.
|
|
93
|
+
const normalized = naive.replace(" ", "T");
|
|
94
|
+
// Append seconds if missing so Date can parse it
|
|
95
|
+
const withSeconds = /T\d{2}:\d{2}$/.test(normalized) ? normalized + ":00" : normalized;
|
|
96
|
+
// Parse as if it were UTC, then compute the offset for the target timezone
|
|
97
|
+
const asUtcDate = new Date(withSeconds + "Z");
|
|
98
|
+
// Get what the target timezone thinks this UTC moment is
|
|
99
|
+
const localStr = asUtcDate.toLocaleString("sv-SE", { timeZone: timezone, hour12: false });
|
|
100
|
+
// localStr is YYYY-MM-DD HH:MM:SS - compare to our input to find the offset
|
|
101
|
+
const localParsed = new Date(localStr.replace(" ", "T") + "Z");
|
|
102
|
+
// offset in ms: localParsed - asUtcDate (positive = ahead of UTC)
|
|
103
|
+
const offsetMs = localParsed.getTime() - asUtcDate.getTime();
|
|
104
|
+
// The actual UTC time = input local time - offset
|
|
105
|
+
const inputLocal = new Date(withSeconds + "Z");
|
|
106
|
+
const utcTime = new Date(inputLocal.getTime() - offsetMs);
|
|
107
|
+
return utcTime.toISOString().slice(0, 16).replace("T", " ");
|
|
108
|
+
}
|
|
109
|
+
/**
|
|
110
|
+
* Create projection tools. When timezone is set, naive datetimes from the
|
|
111
|
+
* agent are converted to UTC before storage.
|
|
112
|
+
*/
|
|
113
|
+
export function createProjectionTools(store, timezone) {
|
|
114
|
+
const projectTool = {
|
|
115
|
+
name: "projection_create",
|
|
116
|
+
label: "projection_create",
|
|
117
|
+
description: "Store a future event, plan, or expectation in projection memory. " +
|
|
118
|
+
"Use when the user mentions anything about the future: appointments, deadlines, " +
|
|
119
|
+
"plans, reminders, or things they intend to do. " +
|
|
120
|
+
"Resolve the time expression to an ISO datetime or date when possible. " +
|
|
121
|
+
"Link related projections using linked_ids.",
|
|
122
|
+
parameters: projectSchema,
|
|
123
|
+
async execute(_toolCallId, { summary, when, resolution, recurrence, trigger_on_fact, context, linked_ids, depends_on }) {
|
|
124
|
+
try {
|
|
125
|
+
let resolved_when;
|
|
126
|
+
let raw_when;
|
|
127
|
+
let res = resolution ?? "day";
|
|
128
|
+
if (when) {
|
|
129
|
+
const isoPattern = /^\d{4}-\d{2}-\d{2}([T ]\d{2}:\d{2})?/;
|
|
130
|
+
if (isoPattern.test(when)) {
|
|
131
|
+
const hasTime = when.includes("T") || (when.length > 10 && when[10] === " ");
|
|
132
|
+
// Normalize to UTC if the string contains a time component
|
|
133
|
+
resolved_when = hasTime ? toUtcDatetime(when, timezone) : when;
|
|
134
|
+
res = hasTime ? "exact" : (resolution ?? "day");
|
|
135
|
+
}
|
|
136
|
+
else if (when === "someday") {
|
|
137
|
+
res = "someday";
|
|
138
|
+
raw_when = when;
|
|
139
|
+
}
|
|
140
|
+
else {
|
|
141
|
+
raw_when = when;
|
|
142
|
+
res = resolution ?? "day";
|
|
143
|
+
}
|
|
144
|
+
}
|
|
145
|
+
const id = store.add({
|
|
146
|
+
summary,
|
|
147
|
+
raw_when,
|
|
148
|
+
resolved_when,
|
|
149
|
+
resolution: res,
|
|
150
|
+
recurrence,
|
|
151
|
+
trigger_on_fact,
|
|
152
|
+
context,
|
|
153
|
+
linked_ids,
|
|
154
|
+
depends_on: depends_on?.map((dep) => ({
|
|
155
|
+
subject_id: dep.projection_id,
|
|
156
|
+
condition: dep.condition,
|
|
157
|
+
condition_type: dep.condition_type,
|
|
158
|
+
})),
|
|
159
|
+
});
|
|
160
|
+
const text = JSON.stringify({ success: true, id }, null, 2);
|
|
161
|
+
return { content: [{ type: "text", text }], details: { success: true, id } };
|
|
162
|
+
}
|
|
163
|
+
catch (error) {
|
|
164
|
+
const err = error;
|
|
165
|
+
const text = JSON.stringify({ error: err.message });
|
|
166
|
+
return { content: [{ type: "text", text }], details: { error: err.message } };
|
|
167
|
+
}
|
|
168
|
+
},
|
|
169
|
+
};
|
|
170
|
+
const getProjectionsTool = {
|
|
171
|
+
name: "projection_list",
|
|
172
|
+
label: "projection_list",
|
|
173
|
+
description: "Retrieve your active (pending) projections. Default horizon is 7 days. " +
|
|
174
|
+
"Always includes someday items. Use to review what's coming up or to find " +
|
|
175
|
+
"IDs for projection_resolve.",
|
|
176
|
+
parameters: getProjectionsSchema,
|
|
177
|
+
async execute(_toolCallId, { horizon_days }) {
|
|
178
|
+
try {
|
|
179
|
+
const days = horizon_days ?? 7;
|
|
180
|
+
const projections = store.getUpcoming(days);
|
|
181
|
+
const text = JSON.stringify({ projections }, null, 2);
|
|
182
|
+
return { content: [{ type: "text", text }], details: { projections } };
|
|
183
|
+
}
|
|
184
|
+
catch (error) {
|
|
185
|
+
const err = error;
|
|
186
|
+
const text = JSON.stringify({ error: err.message });
|
|
187
|
+
return { content: [{ type: "text", text }], details: { error: err.message } };
|
|
188
|
+
}
|
|
189
|
+
},
|
|
190
|
+
};
|
|
191
|
+
const resolveProjectionTool = {
|
|
192
|
+
name: "projection_resolve",
|
|
193
|
+
label: "projection_resolve",
|
|
194
|
+
description: "Mark a projection as resolved. Use 'done' when something happened as expected, " +
|
|
195
|
+
"'cancelled' when a plan fell through, 'passed' when the time passed without confirmation. " +
|
|
196
|
+
"Call this when the user tells you an outcome, or when you observe that a projected " +
|
|
197
|
+
"time has passed.",
|
|
198
|
+
parameters: resolveProjectionSchema,
|
|
199
|
+
async execute(_toolCallId, { id, outcome }) {
|
|
200
|
+
try {
|
|
201
|
+
const found = store.resolve(id, outcome);
|
|
202
|
+
if (!found) {
|
|
203
|
+
const text = JSON.stringify({ error: `Projection not found or already resolved: ${id}` });
|
|
204
|
+
return { content: [{ type: "text", text }], details: { error: "not found" } };
|
|
205
|
+
}
|
|
206
|
+
const text = JSON.stringify({ success: true, id, outcome }, null, 2);
|
|
207
|
+
return { content: [{ type: "text", text }], details: { success: true, id, outcome } };
|
|
208
|
+
}
|
|
209
|
+
catch (error) {
|
|
210
|
+
const err = error;
|
|
211
|
+
const text = JSON.stringify({ error: err.message });
|
|
212
|
+
return { content: [{ type: "text", text }], details: { error: err.message } };
|
|
213
|
+
}
|
|
214
|
+
},
|
|
215
|
+
};
|
|
216
|
+
const linkProjectionTool = {
|
|
217
|
+
name: "projection_link",
|
|
218
|
+
label: "projection_link",
|
|
219
|
+
description: "Create a dependency between two existing projections. " +
|
|
220
|
+
"Use this when the dependency is discovered after both projections already exist.",
|
|
221
|
+
parameters: linkProjectionSchema,
|
|
222
|
+
async execute(_toolCallId, { observer_id, subject_id, condition, condition_type }) {
|
|
223
|
+
try {
|
|
224
|
+
const id = store.linkDependency(observer_id, subject_id, condition, condition_type);
|
|
225
|
+
const text = JSON.stringify({ success: true, id }, null, 2);
|
|
226
|
+
return { content: [{ type: "text", text }], details: { success: true, id } };
|
|
227
|
+
}
|
|
228
|
+
catch (error) {
|
|
229
|
+
const err = error;
|
|
230
|
+
const text = JSON.stringify({ error: err.message });
|
|
231
|
+
return { content: [{ type: "text", text }], details: { error: err.message } };
|
|
232
|
+
}
|
|
233
|
+
},
|
|
234
|
+
};
|
|
235
|
+
return [projectTool, getProjectionsTool, resolveProjectionTool, linkProjectionTool];
|
|
236
|
+
}
|
|
237
|
+
//# sourceMappingURL=tools.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"tools.js","sourceRoot":"","sources":["../../src/projection/tools.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Scheduler: three job types, all driving the agent via synthetic messages.
|
|
3
|
+
*
|
|
4
|
+
* 1. Config-driven jobs (startConfigJobs): cron entries from config.yml. The
|
|
5
|
+
* operator defines the schedule and the message text. Fire unconditionally
|
|
6
|
+
* regardless of active-hours config.
|
|
7
|
+
*
|
|
8
|
+
* 2. Projection daily review (startProjectionJobs — daily): fires at 08:00 UTC
|
|
9
|
+
* every day. Sends the agent a broad "what's coming up?" prompt listing all
|
|
10
|
+
* projections due in the next 7 days. The agent decides what (if anything)
|
|
11
|
+
* to surface to the user.
|
|
12
|
+
*
|
|
13
|
+
* 3. Projection exact-time check (startProjectionJobs — every 5 min): precise
|
|
14
|
+
* trigger for projections with a specific datetime. Checks for anything due
|
|
15
|
+
* within the next 15 minutes. Skips silently outside active hours.
|
|
16
|
+
*
|
|
17
|
+
* All three types construct a synthetic IncomingMessage and pass it to the
|
|
18
|
+
* onMessage callback, which feeds it into the main agent loop exactly as if
|
|
19
|
+
* a real user had sent it.
|
|
20
|
+
*/
|
|
21
|
+
import type { Config } from "./config.js";
|
|
22
|
+
import type { IncomingMessage } from "./channels/types.js";
|
|
23
|
+
export interface Scheduler {
|
|
24
|
+
/** Start all jobs (config-driven and projection-driven). */
|
|
25
|
+
start(): void;
|
|
26
|
+
/** Stop all running jobs. */
|
|
27
|
+
stop(): void;
|
|
28
|
+
}
|
|
29
|
+
/**
|
|
30
|
+
* Create the scheduler.
|
|
31
|
+
*
|
|
32
|
+
* @param config App config (for config.yml cron jobs and the default channel).
|
|
33
|
+
* @param onMessage Callback to inject synthetic messages into the agent loop.
|
|
34
|
+
*/
|
|
35
|
+
export declare function createScheduler(config: Config, onMessage: (msg: IncomingMessage) => Promise<void>): Scheduler;
|
|
36
|
+
//# sourceMappingURL=scheduler.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"scheduler.d.ts","sourceRoot":"","sources":["../src/scheduler.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;GAmBG;AAGH,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AAC1C,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,qBAAqB,CAAC;AAkC3D,MAAM,WAAW,SAAS;IACxB,4DAA4D;IAC5D,KAAK,IAAI,IAAI,CAAC;IAEd,6BAA6B;IAC7B,IAAI,IAAI,IAAI,CAAC;CACd;AAMD;;;;;GAKG;AACH,wBAAgB,eAAe,CAC7B,MAAM,EAAE,MAAM,EACd,SAAS,EAAE,CAAC,GAAG,EAAE,eAAe,KAAK,OAAO,CAAC,IAAI,CAAC,GACjD,SAAS,CA4PX"}
|
|
@@ -0,0 +1,286 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Scheduler: three job types, all driving the agent via synthetic messages.
|
|
3
|
+
*
|
|
4
|
+
* 1. Config-driven jobs (startConfigJobs): cron entries from config.yml. The
|
|
5
|
+
* operator defines the schedule and the message text. Fire unconditionally
|
|
6
|
+
* regardless of active-hours config.
|
|
7
|
+
*
|
|
8
|
+
* 2. Projection daily review (startProjectionJobs — daily): fires at 08:00 UTC
|
|
9
|
+
* every day. Sends the agent a broad "what's coming up?" prompt listing all
|
|
10
|
+
* projections due in the next 7 days. The agent decides what (if anything)
|
|
11
|
+
* to surface to the user.
|
|
12
|
+
*
|
|
13
|
+
* 3. Projection exact-time check (startProjectionJobs — every 5 min): precise
|
|
14
|
+
* trigger for projections with a specific datetime. Checks for anything due
|
|
15
|
+
* within the next 15 minutes. Skips silently outside active hours.
|
|
16
|
+
*
|
|
17
|
+
* All three types construct a synthetic IncomingMessage and pass it to the
|
|
18
|
+
* onMessage callback, which feeds it into the main agent loop exactly as if
|
|
19
|
+
* a real user had sent it.
|
|
20
|
+
*/
|
|
21
|
+
import { Cron } from "croner";
|
|
22
|
+
import { createProjectionStore, formatProjectionsForPrompt, runReflection } from "./projection/index.js";
|
|
23
|
+
import { isActiveNow } from "./active-hours.js";
|
|
24
|
+
// ---------------------------------------------------------------------------
|
|
25
|
+
// Helpers
|
|
26
|
+
// ---------------------------------------------------------------------------
|
|
27
|
+
/**
|
|
28
|
+
* Given a cron expression, calculate the next fire time after `after` and
|
|
29
|
+
* return it as a UTC datetime string suitable for SQLite ("YYYY-MM-DD HH:MM").
|
|
30
|
+
* Returns null if the expression is invalid or produces no next occurrence.
|
|
31
|
+
*
|
|
32
|
+
* Implementation note: croner does not expose a pure "next occurrence"
|
|
33
|
+
* function without constructing a live job. This creates a temporary Cron
|
|
34
|
+
* instance, reads the next run time, then immediately stops it to avoid
|
|
35
|
+
* leaking a running interval.
|
|
36
|
+
*/
|
|
37
|
+
function nextCronOccurrence(cronExpr, after) {
|
|
38
|
+
try {
|
|
39
|
+
const job = new Cron(cronExpr, { timezone: "UTC", startAt: after });
|
|
40
|
+
const next = job.nextRun(after);
|
|
41
|
+
job.stop();
|
|
42
|
+
if (!next)
|
|
43
|
+
return null;
|
|
44
|
+
return next.toISOString().slice(0, 16).replace("T", " ");
|
|
45
|
+
}
|
|
46
|
+
catch {
|
|
47
|
+
return null;
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
// ---------------------------------------------------------------------------
|
|
51
|
+
// Factory
|
|
52
|
+
// ---------------------------------------------------------------------------
|
|
53
|
+
/**
|
|
54
|
+
* Create the scheduler.
|
|
55
|
+
*
|
|
56
|
+
* @param config App config (for config.yml cron jobs and the default channel).
|
|
57
|
+
* @param onMessage Callback to inject synthetic messages into the agent loop.
|
|
58
|
+
*/
|
|
59
|
+
export function createScheduler(config, onMessage) {
|
|
60
|
+
const cronJobs = new Map();
|
|
61
|
+
function defaultChannelId() {
|
|
62
|
+
const firstUser = config.telegram.allowed_users[0];
|
|
63
|
+
return firstUser ? String(firstUser) : "cron";
|
|
64
|
+
}
|
|
65
|
+
function startConfigJobs() {
|
|
66
|
+
for (let i = 0; i < config.cron.length; i++) {
|
|
67
|
+
const cronJob = config.cron[i];
|
|
68
|
+
const key = `config-${i}`;
|
|
69
|
+
try {
|
|
70
|
+
const job = new Cron(cronJob.schedule, async () => {
|
|
71
|
+
console.log(`[scheduler] Config job triggered: ${cronJob.schedule}`);
|
|
72
|
+
const channelId = defaultChannelId();
|
|
73
|
+
// raw.type identifies this as a scheduler message. processMessage() in
|
|
74
|
+
// index.ts checks for this field to skip crash-recovery checkpoints
|
|
75
|
+
// that only make sense for real user messages.
|
|
76
|
+
const msg = {
|
|
77
|
+
channelId,
|
|
78
|
+
userId: "cron",
|
|
79
|
+
text: cronJob.message,
|
|
80
|
+
platform: "telegram",
|
|
81
|
+
raw: { type: "cron", schedule: cronJob.schedule },
|
|
82
|
+
};
|
|
83
|
+
await onMessage(msg);
|
|
84
|
+
}, { timezone: "UTC" });
|
|
85
|
+
cronJobs.set(key, job);
|
|
86
|
+
const preview = cronJob.message.length > 50
|
|
87
|
+
? `${cronJob.message.substring(0, 50)}...`
|
|
88
|
+
: cronJob.message;
|
|
89
|
+
console.log(`[scheduler] Config job scheduled: ${cronJob.schedule} -> ${preview}`);
|
|
90
|
+
}
|
|
91
|
+
catch (err) {
|
|
92
|
+
console.error(`[scheduler] Failed to schedule config job: ${cronJob.schedule}`, err);
|
|
93
|
+
}
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
/**
|
|
97
|
+
* Two projection jobs for the primary user:
|
|
98
|
+
*
|
|
99
|
+
* - Daily review at 8am UTC: a broad "what's coming up?" pass. The agent
|
|
100
|
+
* receives all projections due in the next 7 days and decides what to
|
|
101
|
+
* surface. Outside active hours the job silently skips — the review is
|
|
102
|
+
* informational, not time-critical.
|
|
103
|
+
*
|
|
104
|
+
* - Exact-time check every 5 min: a precise trigger for projections that
|
|
105
|
+
* have a specific datetime (resolution='exact'). Only fires when something
|
|
106
|
+
* is actually due; skips silently outside active hours.
|
|
107
|
+
*
|
|
108
|
+
* The daily review is intentionally broad and agent-mediated; the exact-time
|
|
109
|
+
* check is a direct trigger for a concrete commitment. Both are distinct from
|
|
110
|
+
* config-driven jobs, which fire unconditionally and carry operator-authored
|
|
111
|
+
* message text.
|
|
112
|
+
*/
|
|
113
|
+
function startProjectionJobs() {
|
|
114
|
+
const primaryUserId = String(config.telegram.allowed_users[0] ?? "");
|
|
115
|
+
if (!primaryUserId || primaryUserId === "undefined") {
|
|
116
|
+
console.warn("[projections] No primary user configured (telegram.allowed_users is empty) — projection jobs not started");
|
|
117
|
+
return;
|
|
118
|
+
}
|
|
119
|
+
const channelId = defaultChannelId();
|
|
120
|
+
// Daily review: 8am UTC every day
|
|
121
|
+
const dailyJob = new Cron("0 8 * * *", async () => {
|
|
122
|
+
// Projection jobs respect active hours; config-driven jobs do not.
|
|
123
|
+
// This asymmetry is intentional: config jobs are operator-controlled
|
|
124
|
+
// and may need to fire at any time (e.g., system maintenance notices),
|
|
125
|
+
// while projection jobs are conversational and should not wake the user.
|
|
126
|
+
if (!isActiveNow(config.active_hours)) {
|
|
127
|
+
console.log("[projections] Daily review skipped (outside active hours)");
|
|
128
|
+
return;
|
|
129
|
+
}
|
|
130
|
+
console.log("[projections] Daily review triggered");
|
|
131
|
+
const store = createProjectionStore(primaryUserId, config.data_dir);
|
|
132
|
+
try {
|
|
133
|
+
const expired = store.autoExpire(24);
|
|
134
|
+
if (expired > 0) {
|
|
135
|
+
console.log(`[projections] Auto-expired ${expired} stale projection(s)`);
|
|
136
|
+
}
|
|
137
|
+
const activated = store.evaluateDependencies();
|
|
138
|
+
if (activated > 0) {
|
|
139
|
+
console.log(`[projections] Activated ${activated} projection(s) via dependencies`);
|
|
140
|
+
}
|
|
141
|
+
const upcoming = store.getUpcoming(7);
|
|
142
|
+
if (upcoming.length === 0) {
|
|
143
|
+
console.log("[projections] Daily review: no upcoming projections, skipping");
|
|
144
|
+
return;
|
|
145
|
+
}
|
|
146
|
+
const formatted = formatProjectionsForPrompt(upcoming, 20);
|
|
147
|
+
// raw.type marks this as a scheduler message so processMessage() can
|
|
148
|
+
// distinguish it from a real user message and skip crash checkpoints.
|
|
149
|
+
const msg = {
|
|
150
|
+
channelId,
|
|
151
|
+
userId: primaryUserId,
|
|
152
|
+
text: `[Daily review]\n\nHere is what's coming up:\n\n${formatted}\n\n` +
|
|
153
|
+
`Review each item. For each projection, decide whether to surface it TODAY:\n` +
|
|
154
|
+
`1. Search your memory for related context (use memory_archival_search)\n` +
|
|
155
|
+
`2. If due today or overdue: compose a message or take action.\n` +
|
|
156
|
+
`3. If due later this week: surface only if today is the right day for it.\n` +
|
|
157
|
+
`4. If further out: only act if something needs attention now.\n` +
|
|
158
|
+
`5. If cancelled, resolved, or clearly passed: resolve it and move on.\n` +
|
|
159
|
+
`6. If nothing needs to happen: say nothing (NOOP is fine).\n\n` +
|
|
160
|
+
`Timing rules:\n` +
|
|
161
|
+
`- If a task has a hard deadline AND an unresolved blocker (waiting on someone, missing info), ` +
|
|
162
|
+
`surface it EARLY so the user can start unblocking. Don't wait for the blocker to resolve itself.\n` +
|
|
163
|
+
`- If today is a light day and a task is due this week, today is probably a good day to surface it. ` +
|
|
164
|
+
`Don't skip it just because other days look busy.\n` +
|
|
165
|
+
`- Only defer if today is genuinely a bad day (too busy, user is overwhelmed, or a later day is ` +
|
|
166
|
+
`clearly better for a specific reason).`,
|
|
167
|
+
platform: "telegram",
|
|
168
|
+
raw: { type: "projection_daily_review" },
|
|
169
|
+
};
|
|
170
|
+
await onMessage(msg);
|
|
171
|
+
}
|
|
172
|
+
finally {
|
|
173
|
+
store.close();
|
|
174
|
+
}
|
|
175
|
+
}, { timezone: "UTC" });
|
|
176
|
+
cronJobs.set("projection-daily", dailyJob);
|
|
177
|
+
console.log("[projections] Daily review scheduled at 08:00 UTC");
|
|
178
|
+
// Exact-time check: every 5 minutes
|
|
179
|
+
const exactJob = new Cron("*/5 * * * *", async () => {
|
|
180
|
+
if (!isActiveNow(config.active_hours)) {
|
|
181
|
+
return; // Silent skip - fires every 5 min, no need to log each one
|
|
182
|
+
}
|
|
183
|
+
const store = createProjectionStore(primaryUserId, config.data_dir);
|
|
184
|
+
try {
|
|
185
|
+
store.evaluateDependencies();
|
|
186
|
+
const due = store.getExactDue(15);
|
|
187
|
+
if (due.length === 0) {
|
|
188
|
+
return;
|
|
189
|
+
}
|
|
190
|
+
console.log(`[projections] Exact-time check: ${due.length} item(s) due`);
|
|
191
|
+
const formatted = formatProjectionsForPrompt(due, 10);
|
|
192
|
+
// Settle each projection: rearm recurring ones, mark one-offs as passed.
|
|
193
|
+
const now = new Date();
|
|
194
|
+
for (const p of due) {
|
|
195
|
+
if (p.recurrence) {
|
|
196
|
+
const next = nextCronOccurrence(p.recurrence, now);
|
|
197
|
+
if (next) {
|
|
198
|
+
store.rearm(p.id, next);
|
|
199
|
+
console.log(`[projections] Rearmed recurring projection ${p.id} → next: ${next}`);
|
|
200
|
+
}
|
|
201
|
+
else {
|
|
202
|
+
// Cron produced no future occurrence — treat as one-off.
|
|
203
|
+
store.resolve(p.id, "passed");
|
|
204
|
+
console.warn(`[projections] Recurring projection ${p.id} produced no next occurrence, marked passed`);
|
|
205
|
+
}
|
|
206
|
+
}
|
|
207
|
+
else {
|
|
208
|
+
store.resolve(p.id, "passed");
|
|
209
|
+
}
|
|
210
|
+
}
|
|
211
|
+
// raw.type marks this as a scheduler message so processMessage() can
|
|
212
|
+
// distinguish it from a real user message and skip crash checkpoints.
|
|
213
|
+
const msg = {
|
|
214
|
+
channelId,
|
|
215
|
+
userId: primaryUserId,
|
|
216
|
+
text: `[Scheduled reminder]\n\nThe following reminder(s) are due now:\n\n` +
|
|
217
|
+
`${formatted}\n\n` +
|
|
218
|
+
`For each item:\n` +
|
|
219
|
+
`1. Search your memory for related context (use memory_archival_search)\n` +
|
|
220
|
+
`2. Send the user a helpful, natural message — or reply NOOP if nothing needs to be said.`,
|
|
221
|
+
platform: "telegram",
|
|
222
|
+
raw: { type: "projection_exact_check" },
|
|
223
|
+
};
|
|
224
|
+
await onMessage(msg);
|
|
225
|
+
}
|
|
226
|
+
finally {
|
|
227
|
+
store.close();
|
|
228
|
+
}
|
|
229
|
+
}, { timezone: "UTC" });
|
|
230
|
+
cronJobs.set("projection-exact", exactJob);
|
|
231
|
+
console.log("[projections] Exact-time check scheduled every 5 minutes");
|
|
232
|
+
}
|
|
233
|
+
/**
|
|
234
|
+
* Reflection cron: every 30 minutes, scan recent conversation for future
|
|
235
|
+
* references the agent missed. Writes projections directly to SQLite
|
|
236
|
+
* without touching the agent loop. Skips when there are no new messages.
|
|
237
|
+
*/
|
|
238
|
+
function startReflectionJob() {
|
|
239
|
+
const primaryUserId = String(config.telegram.allowed_users[0] ?? "");
|
|
240
|
+
if (!primaryUserId || primaryUserId === "undefined") {
|
|
241
|
+
return;
|
|
242
|
+
}
|
|
243
|
+
const job = new Cron("*/30 * * * *", async () => {
|
|
244
|
+
try {
|
|
245
|
+
const result = await runReflection(config, primaryUserId, 30);
|
|
246
|
+
if (result.skipped) {
|
|
247
|
+
// Only log at debug level — this fires often and is usually a no-op
|
|
248
|
+
return;
|
|
249
|
+
}
|
|
250
|
+
if (result.projectionsAdded > 0) {
|
|
251
|
+
console.log(`[reflection] Added ${result.projectionsAdded} projection(s) from recent conversation`);
|
|
252
|
+
}
|
|
253
|
+
else {
|
|
254
|
+
console.log("[reflection] No new projections found in recent conversation");
|
|
255
|
+
}
|
|
256
|
+
}
|
|
257
|
+
catch (err) {
|
|
258
|
+
console.error("[reflection] Unhandled error:", err.message);
|
|
259
|
+
}
|
|
260
|
+
}, { timezone: "UTC" });
|
|
261
|
+
cronJobs.set("projection-reflection", job);
|
|
262
|
+
console.log("[projections] Reflection pass scheduled every 30 minutes");
|
|
263
|
+
}
|
|
264
|
+
return {
|
|
265
|
+
start() {
|
|
266
|
+
startConfigJobs();
|
|
267
|
+
startProjectionJobs();
|
|
268
|
+
startReflectionJob();
|
|
269
|
+
const total = cronJobs.size;
|
|
270
|
+
if (total > 0) {
|
|
271
|
+
console.log(`[scheduler] Started ${total} jobs (${config.cron.length} config, rest projection)`);
|
|
272
|
+
}
|
|
273
|
+
},
|
|
274
|
+
stop() {
|
|
275
|
+
for (const job of cronJobs.values()) {
|
|
276
|
+
job.stop();
|
|
277
|
+
}
|
|
278
|
+
const count = cronJobs.size;
|
|
279
|
+
cronJobs.clear();
|
|
280
|
+
if (count > 0) {
|
|
281
|
+
console.log(`[scheduler] Stopped ${count} jobs`);
|
|
282
|
+
}
|
|
283
|
+
},
|
|
284
|
+
};
|
|
285
|
+
}
|
|
286
|
+
//# sourceMappingURL=scheduler.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"scheduler.js","sourceRoot":"","sources":["../src/scheduler.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* System prompt assembly for the agent.
|
|
3
|
+
*
|
|
4
|
+
* Builds the complete system prompt from config, core memory, tools,
|
|
5
|
+
* projections, and behavioral instructions. This is prompt engineering
|
|
6
|
+
* separated from session management to make iteration easier.
|
|
7
|
+
*/
|
|
8
|
+
import type { Config } from "./config.js";
|
|
9
|
+
/**
|
|
10
|
+
* Summary of a tool for the system prompt listing.
|
|
11
|
+
*/
|
|
12
|
+
export interface ToolSummary {
|
|
13
|
+
name: string;
|
|
14
|
+
description?: string;
|
|
15
|
+
}
|
|
16
|
+
/**
|
|
17
|
+
* Token used to signal that there is nothing to say in a scheduled/proactive turn.
|
|
18
|
+
*/
|
|
19
|
+
export declare const SILENT_REPLY_TOKEN = "NOOP";
|
|
20
|
+
/**
|
|
21
|
+
* Build the tool listing section of the system prompt.
|
|
22
|
+
*/
|
|
23
|
+
export declare function buildToolSection(tools: ToolSummary[], extensionToolNames: Set<string>): string;
|
|
24
|
+
/**
|
|
25
|
+
* Build the complete system prompt from config, core memory, tools, and projections.
|
|
26
|
+
*
|
|
27
|
+
* This function assembles all the sections that make up the agent's system prompt:
|
|
28
|
+
* - Base system prompt from config
|
|
29
|
+
* - Image handling capabilities
|
|
30
|
+
* - Current date and time (with timezone if configured)
|
|
31
|
+
* - Communication style and tool call guidelines
|
|
32
|
+
* - Tool listings (including extension tools)
|
|
33
|
+
* - Extension management instructions
|
|
34
|
+
* - Skill management instructions
|
|
35
|
+
* - Core memory
|
|
36
|
+
* - Projections (upcoming events and commitments)
|
|
37
|
+
* - Background worker instructions
|
|
38
|
+
* - Silent reply mechanism
|
|
39
|
+
*/
|
|
40
|
+
export declare function buildSystemPrompt(config: Config, coreMemory: string, tools: ToolSummary[], extensionToolNames: Set<string>, projections: string): string;
|
|
41
|
+
//# sourceMappingURL=system-prompt.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"system-prompt.d.ts","sourceRoot":"","sources":["../src/system-prompt.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,aAAa,CAAC;AAE1C;;GAEG;AACH,MAAM,WAAW,WAAW;IAC1B,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED;;GAEG;AACH,eAAO,MAAM,kBAAkB,SAAS,CAAC;AAEzC;;GAEG;AACH,wBAAgB,gBAAgB,CAC9B,KAAK,EAAE,WAAW,EAAE,EACpB,kBAAkB,EAAE,GAAG,CAAC,MAAM,CAAC,GAC9B,MAAM,CAgBR;AAED;;;;;;;;;;;;;;;GAeG;AACH,wBAAgB,iBAAiB,CAC/B,MAAM,EAAE,MAAM,EACd,UAAU,EAAE,MAAM,EAClB,KAAK,EAAE,WAAW,EAAE,EACpB,kBAAkB,EAAE,GAAG,CAAC,MAAM,CAAC,EAC/B,WAAW,EAAE,MAAM,GAClB,MAAM,CA4IR"}
|