tandem-mode 0.1.4 → 0.4.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/README.md +37 -1
- package/README.sr.md +37 -1
- package/dist/agent/clipboard.js +4 -5
- package/dist/agent/clipboard.js.map +1 -1
- package/dist/agent/compact.js +80 -0
- package/dist/agent/compact.js.map +1 -0
- package/dist/agent/loop.js +2 -2
- package/dist/agent/loop.js.map +1 -1
- package/dist/agent/tools/edit.js +11 -11
- package/dist/agent/tools/edit.js.map +1 -1
- package/dist/agent/tools/gitDiff.js +41 -18
- package/dist/agent/tools/gitDiff.js.map +1 -1
- package/dist/agent/tools/listDir.js +4 -4
- package/dist/agent/tools/listDir.js.map +1 -1
- package/dist/agent/tools/readFile.js +7 -7
- package/dist/agent/tools/readFile.js.map +1 -1
- package/dist/agent/tools/search.js +10 -10
- package/dist/agent/tools/search.js.map +1 -1
- package/dist/agent/tools/shell.js +32 -14
- package/dist/agent/tools/shell.js.map +1 -1
- package/dist/agent/tools/viewImage.js +4 -4
- package/dist/agent/tools/viewImage.js.map +1 -1
- package/dist/agent/tools/webSearch.js +3 -3
- package/dist/agent/tools/webSearch.js.map +1 -1
- package/dist/benchmark/runner.js.map +1 -1
- package/dist/benchmark/tasks/{bitwiseBulkPriceWizard.js → bulkPriceWizard.js} +3 -3
- package/dist/benchmark/tasks/bulkPriceWizard.js.map +1 -0
- package/dist/cli.js +48 -22
- package/dist/cli.js.map +1 -1
- package/dist/config/credentials.js +5 -5
- package/dist/config/credentials.js.map +1 -1
- package/dist/config/profiles.js +108 -0
- package/dist/config/profiles.js.map +1 -0
- package/dist/config/schema.js.map +1 -1
- package/dist/deepseek/vision.js +4 -4
- package/dist/deepseek/vision.js.map +1 -1
- package/dist/deepseek/webSearch.js +1 -1
- package/dist/i18n/en.js +103 -0
- package/dist/i18n/en.js.map +1 -0
- package/dist/i18n/index.js +23 -0
- package/dist/i18n/index.js.map +1 -0
- package/dist/i18n/sr.js +101 -0
- package/dist/i18n/sr.js.map +1 -0
- package/dist/orchestrator/notify.js +38 -0
- package/dist/orchestrator/notify.js.map +1 -0
- package/dist/orchestrator/orchestrate.js +50 -19
- package/dist/orchestrator/orchestrate.js.map +1 -1
- package/dist/orchestrator/planner.js +10 -10
- package/dist/orchestrator/planner.js.map +1 -1
- package/dist/orchestrator/repoMap.js +1 -1
- package/dist/orchestrator/repoMap.js.map +1 -1
- package/dist/orchestrator/reviewer.js +20 -12
- package/dist/orchestrator/reviewer.js.map +1 -1
- package/dist/repl/commands.js +122 -37
- package/dist/repl/commands.js.map +1 -1
- package/dist/repl/system-prompt.js +13 -11
- package/dist/repl/system-prompt.js.map +1 -1
- package/dist/repl/wizard.js +17 -9
- package/dist/repl/wizard.js.map +1 -1
- package/package.json +1 -1
- package/dist/benchmark/tasks/bitwiseBulkPriceWizard.js.map +0 -1
package/README.md
CHANGED
|
@@ -128,9 +128,13 @@ tandem "task" --model deepseek-v4-flash --effort low --budget 0.50 --yes
|
|
|
128
128
|
| `/thinking [on\|off]` | Toggle thinking mode |
|
|
129
129
|
| `/effort [low\|high\|max]` | Show or set reasoning effort |
|
|
130
130
|
| `/status` | Current session/settings |
|
|
131
|
+
| `/diff [--staged] [path]` | Working-tree diff, no API call |
|
|
131
132
|
| `/usage` | Tokens, cost, off-peak projection |
|
|
132
133
|
| `/budget [amount]` | Show or set the session budget |
|
|
133
134
|
| `/new` | Start a fresh session |
|
|
135
|
+
| `/save-profile <name>` | Save model, effort, budget and review loops as a named profile |
|
|
136
|
+
| `/profile [name]` | Load a saved profile, or list them |
|
|
137
|
+
| `/compact` | Summarize the history into a new session to free up context; the old session stays on disk |
|
|
134
138
|
| `/fork` | New session, carrying over the current history |
|
|
135
139
|
| `/resume [id]` | Continue the latest (or a named) session |
|
|
136
140
|
| `/paste [message]` | Send a clipboard image to the agent |
|
|
@@ -170,10 +174,42 @@ in the current directory) > **global** (`~/.tandem/config.json`).
|
|
|
170
174
|
"defaultModel": "deepseek-v4-pro",
|
|
171
175
|
"defaultReasoningEffort": "high",
|
|
172
176
|
"budgetUsd": 5,
|
|
173
|
-
"maxReviewLoops": 3
|
|
177
|
+
"maxReviewLoops": 3,
|
|
178
|
+
"verifyCommand": "pnpm typecheck && pnpm test",
|
|
179
|
+
"notifyCommand": "curl -s -d \"Tandem: $TANDEM_OUTCOME\" https://ntfy.sh/my-topic",
|
|
180
|
+
"language": "en"
|
|
174
181
|
}
|
|
175
182
|
```
|
|
176
183
|
|
|
184
|
+
`verifyCommand` runs before each `/plan` review round and its result goes to
|
|
185
|
+
the reviewer. `language` is the UI language (`en` or `sr`, default `en`); the
|
|
186
|
+
`--lang` flag and the `TANDEM_LANG` environment variable override it, in that
|
|
187
|
+
order. The first-run wizard asks for it.
|
|
188
|
+
|
|
189
|
+
`notifyCommand` runs when a `/plan` run ends: reviewer approved, `max_review_loops`
|
|
190
|
+
reached, or an error (not when you interrupt it with ESC). The details come in as
|
|
191
|
+
environment variables, never spliced into the command text: `TANDEM_OUTCOME`
|
|
192
|
+
(`approved`, `max_review_loops` or `error`), `TANDEM_TASK`, `TANDEM_NOTES` (the
|
|
193
|
+
reviewer's notes, or the error message), `TANDEM_REVIEW_LOOPS` and `TANDEM_COST_USD`.
|
|
194
|
+
The command runs in your shell (PowerShell on Windows, `sh` elsewhere) with a 15 s
|
|
195
|
+
limit, and a failure only prints a warning. Any shell command works, so Slack,
|
|
196
|
+
ntfy, a desktop notification or a webhook are all just examples:
|
|
197
|
+
|
|
198
|
+
```json
|
|
199
|
+
{ "notifyCommand": "curl -s -d \"Tandem: $TANDEM_OUTCOME\" https://ntfy.sh/my-topic" }
|
|
200
|
+
```
|
|
201
|
+
|
|
202
|
+
On Windows (PowerShell) the variables are written `$env:TANDEM_OUTCOME`.
|
|
203
|
+
|
|
204
|
+
Like `verifyCommand`, `notifyCommand` runs without asking, so only put it in a
|
|
205
|
+
project's `.tandem/config.json` if you trust that project.
|
|
206
|
+
|
|
207
|
+
**Profiles:** `/save-profile <name>` stores the current model, reasoning effort,
|
|
208
|
+
budget and review loops in `~/.tandem/profiles/<name>.json`, and `/profile <name>`
|
|
209
|
+
loads them back into the running session (only the fields present in the file are
|
|
210
|
+
applied). `/profile` alone lists the saved ones. Names use `a-z`, `0-9`, `-` and `_`.
|
|
211
|
+
Profiles never include `verifyCommand` or the API key.
|
|
212
|
+
|
|
177
213
|
The API key is never stored in these files — it lives in the OS credential
|
|
178
214
|
store (or `DEEPSEEK_API_KEY` env var, which takes priority, for CI use).
|
|
179
215
|
|
package/README.sr.md
CHANGED
|
@@ -130,9 +130,13 @@ tandem "task" --model deepseek-v4-flash --effort low --budget 0.50 --yes
|
|
|
130
130
|
| `/thinking [on\|off]` | Uključi/isključi thinking mode |
|
|
131
131
|
| `/effort [low\|high\|max]` | Prikaži ili postavi reasoning effort |
|
|
132
132
|
| `/status` | Trenutna sesija/podešavanja |
|
|
133
|
+
| `/diff [--staged] [putanja]` | Diff radnog stabla, bez API poziva |
|
|
133
134
|
| `/usage` | Tokeni, cena, off-peak projekcija |
|
|
134
135
|
| `/budget [iznos]` | Prikaži ili postavi budžet sesije |
|
|
135
136
|
| `/new` | Nova sesija |
|
|
137
|
+
| `/save-profile <ime>` | Sačuvaj model, effort, budžet i review krugove kao imenovan profil |
|
|
138
|
+
| `/profile [ime]` | Učitaj sačuvan profil, ili prikaži listu |
|
|
139
|
+
| `/compact` | Sažmi istoriju u novu sesiju da se oslobodi kontekst; stara sesija ostaje na disku |
|
|
136
140
|
| `/fork` | Nova sesija sa kopijom trenutne istorije |
|
|
137
141
|
| `/resume [id]` | Nastavi poslednju (ili navedenu) sesiju |
|
|
138
142
|
| `/paste [poruka]` | Pošalji sliku iz clipboard-a agentu |
|
|
@@ -173,10 +177,42 @@ Slojevito: **sesija** (komande u REPL-u) > **projekat**
|
|
|
173
177
|
"defaultModel": "deepseek-v4-pro",
|
|
174
178
|
"defaultReasoningEffort": "high",
|
|
175
179
|
"budgetUsd": 5,
|
|
176
|
-
"maxReviewLoops": 3
|
|
180
|
+
"maxReviewLoops": 3,
|
|
181
|
+
"verifyCommand": "pnpm typecheck && pnpm test",
|
|
182
|
+
"notifyCommand": "curl -s -d \"Tandem: $TANDEM_OUTCOME\" https://ntfy.sh/my-topic",
|
|
183
|
+
"language": "sr"
|
|
177
184
|
}
|
|
178
185
|
```
|
|
179
186
|
|
|
187
|
+
`verifyCommand` se pokreće pre svakog `/plan` review kruga, a njegov rezultat
|
|
188
|
+
ide reviewer-u. `language` je jezik interfejsa (`en` ili `sr`, podrazumevano
|
|
189
|
+
`en`); `--lang` flag i `TANDEM_LANG` env promenljiva ga nadjačavaju, tim
|
|
190
|
+
redom. First-run wizard ga pita.
|
|
191
|
+
|
|
192
|
+
`notifyCommand` se pokreće kad se `/plan` završi: reviewer odobrio, dostignut
|
|
193
|
+
`max_review_loops`, ili greška (ne i kad ga prekineš sa ESC). Detalji dolaze kao
|
|
194
|
+
promenljive okruženja, nikad ubačeni u tekst komande: `TANDEM_OUTCOME`
|
|
195
|
+
(`approved`, `max_review_loops` ili `error`), `TANDEM_TASK`, `TANDEM_NOTES`
|
|
196
|
+
(beleške reviewer-a, ili poruka greške), `TANDEM_REVIEW_LOOPS` i `TANDEM_COST_USD`.
|
|
197
|
+
Komanda radi u tvojoj školjki (PowerShell na Windows-u, `sh` drugde) sa limitom
|
|
198
|
+
od 15 s, a neuspeh samo ispiše upozorenje. Može bilo koja shell komanda, pa su
|
|
199
|
+
Slack, ntfy, desktop obaveštenje ili webhook samo primeri:
|
|
200
|
+
|
|
201
|
+
```json
|
|
202
|
+
{ "notifyCommand": "curl -s -d \"Tandem: $TANDEM_OUTCOME\" https://ntfy.sh/my-topic" }
|
|
203
|
+
```
|
|
204
|
+
|
|
205
|
+
Na Windows-u (PowerShell) promenljive se pišu `$env:TANDEM_OUTCOME`.
|
|
206
|
+
|
|
207
|
+
Kao i `verifyCommand`, `notifyCommand` se pokreće bez pitanja, pa ga stavljaj u
|
|
208
|
+
`.tandem/config.json` projekta samo ako tom projektu veruješ.
|
|
209
|
+
|
|
210
|
+
**Profili:** `/save-profile <ime>` čuva trenutni model, reasoning effort, budžet i
|
|
211
|
+
review krugove u `~/.tandem/profiles/<ime>.json`, a `/profile <ime>` ih vraća u
|
|
212
|
+
sesiju koja radi (primenjuju se samo polja koja postoje u fajlu). `/profile` bez
|
|
213
|
+
argumenta prikazuje sačuvane. Imena koriste `a-z`, `0-9`, `-` i `_`.
|
|
214
|
+
Profili nikad ne sadrže `verifyCommand` ni API ključ.
|
|
215
|
+
|
|
180
216
|
API ključ se nikad ne čuva u ovim fajlovima — živi u OS-ovom skladištu
|
|
181
217
|
kredencijala (ili u `DEEPSEEK_API_KEY` env promenljivoj, koja ima
|
|
182
218
|
prioritet, za CI upotrebu).
|
package/dist/agent/clipboard.js
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { execFile, spawn } from "node:child_process";
|
|
2
|
+
import { t } from "../i18n/index.js";
|
|
2
3
|
import { promisify } from "node:util";
|
|
3
4
|
import { unlink } from "node:fs/promises";
|
|
4
5
|
const execFileAsync = promisify(execFile);
|
|
@@ -88,10 +89,8 @@ async function saveClipboardImageLinux(destPath) {
|
|
|
88
89
|
: ["-selection", "clipboard", "-t", "image/png", "-o"];
|
|
89
90
|
const result = await readBinaryStdout(cmd, args);
|
|
90
91
|
if (result.kind === "not-found") {
|
|
91
|
-
const hint = isWayland
|
|
92
|
-
|
|
93
|
-
: "Instaliraj xclip (npr. sudo apt install xclip).";
|
|
94
|
-
throw new Error(`Komanda "${cmd}" nije pronađena. ${hint}`);
|
|
92
|
+
const hint = isWayland ? t("clipboardInstallWl") : t("clipboardInstallXclip");
|
|
93
|
+
throw new Error(t("clipboardCmdNotFound", { cmd, hint }));
|
|
95
94
|
}
|
|
96
95
|
if (result.kind === "empty")
|
|
97
96
|
return false;
|
|
@@ -108,7 +107,7 @@ export async function saveClipboardImage(destPath) {
|
|
|
108
107
|
case "linux":
|
|
109
108
|
return saveClipboardImageLinux(destPath);
|
|
110
109
|
default:
|
|
111
|
-
throw new Error(
|
|
110
|
+
throw new Error(t("clipboardUnsupported", { platform: process.platform }));
|
|
112
111
|
}
|
|
113
112
|
}
|
|
114
113
|
//# sourceMappingURL=clipboard.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"clipboard.js","sourceRoot":"","sources":["../../src/agent/clipboard.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"clipboard.js","sourceRoot":"","sources":["../../src/agent/clipboard.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
import { chatCompletionOnce } from "../deepseek/client.js";
|
|
2
|
+
// Tool output is where long sessions grow (file dumps, shell output), so it is
|
|
3
|
+
// cut hard in the transcript the summarizer sees. The summary only needs the gist.
|
|
4
|
+
const MAX_TOOL_OUTPUT_CHARS = 1_500;
|
|
5
|
+
const MAX_TOOL_ARGS_CHARS = 300;
|
|
6
|
+
const MAX_TRANSCRIPT_CHARS = 300_000;
|
|
7
|
+
export const SUMMARY_MODEL = "deepseek-v4-flash";
|
|
8
|
+
const SUMMARIZER_SYSTEM_PROMPT = `You compact the history of a coding-agent session so work can continue from your
|
|
9
|
+
summary alone. Write a dense summary with these parts, skipping any that are empty:
|
|
10
|
+
- Goal: what the user is trying to achieve, plus constraints and preferences they stated.
|
|
11
|
+
- Done: files read or changed (exact paths), commands run and their results.
|
|
12
|
+
- Decisions: what was decided and why.
|
|
13
|
+
- State: where things stand right now, including failing tests or errors still open.
|
|
14
|
+
- Next: what was about to happen or is still to do.
|
|
15
|
+
Keep exact file paths, identifiers and error messages that matter. Do not invent anything
|
|
16
|
+
that is not in the conversation. No preamble. Reply in the language the user wrote in.`;
|
|
17
|
+
export const SUMMARY_PREFIX = "Summary of our conversation so far (the earlier messages were compacted to save context):";
|
|
18
|
+
const SUMMARY_ACK = "Understood. I'll continue from this summary.";
|
|
19
|
+
function truncate(text, max) {
|
|
20
|
+
return text.length > max ? `${text.slice(0, max)} … (truncated, ${text.length} chars)` : text;
|
|
21
|
+
}
|
|
22
|
+
/** Plain-text rendering of the history. Text avoids tool_call/tool pairing rules in the summarizer request. */
|
|
23
|
+
export function buildTranscript(messages) {
|
|
24
|
+
const toolNames = new Map();
|
|
25
|
+
for (const m of messages) {
|
|
26
|
+
for (const call of m.toolCalls ?? [])
|
|
27
|
+
toolNames.set(call.id, call.function.name);
|
|
28
|
+
}
|
|
29
|
+
const parts = [];
|
|
30
|
+
for (const m of messages) {
|
|
31
|
+
if (m.role === "system")
|
|
32
|
+
continue;
|
|
33
|
+
if (m.role === "user") {
|
|
34
|
+
parts.push(`USER:\n${m.content ?? ""}`);
|
|
35
|
+
}
|
|
36
|
+
else if (m.role === "assistant") {
|
|
37
|
+
const calls = (m.toolCalls ?? [])
|
|
38
|
+
.map((c) => `[called ${c.function.name}(${truncate(c.function.arguments, MAX_TOOL_ARGS_CHARS)})]`)
|
|
39
|
+
.join("\n");
|
|
40
|
+
const text = [m.content ?? "", calls].filter(Boolean).join("\n");
|
|
41
|
+
if (text)
|
|
42
|
+
parts.push(`ASSISTANT:\n${text}`);
|
|
43
|
+
}
|
|
44
|
+
else {
|
|
45
|
+
const name = (m.toolCallId && toolNames.get(m.toolCallId)) || "tool";
|
|
46
|
+
parts.push(`TOOL RESULT (${name}):\n${truncate(m.content ?? "", MAX_TOOL_OUTPUT_CHARS)}`);
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
const transcript = parts.join("\n\n");
|
|
50
|
+
if (transcript.length <= MAX_TRANSCRIPT_CHARS)
|
|
51
|
+
return transcript;
|
|
52
|
+
// Too long even after trimming tool output: keep the most recent part.
|
|
53
|
+
return `[earlier part of the conversation omitted]\n\n${transcript.slice(-MAX_TRANSCRIPT_CHARS)}`;
|
|
54
|
+
}
|
|
55
|
+
/** One model call. Throws on API errors or an empty summary; the caller's history is never touched here. */
|
|
56
|
+
export async function compactConversation(env, messages, systemPrompt, signal) {
|
|
57
|
+
const response = await chatCompletionOnce(env, {
|
|
58
|
+
model: SUMMARY_MODEL,
|
|
59
|
+
messages: [
|
|
60
|
+
{ role: "system", content: SUMMARIZER_SYSTEM_PROMPT },
|
|
61
|
+
{ role: "user", content: `Conversation to summarize:\n\n${buildTranscript(messages)}` },
|
|
62
|
+
],
|
|
63
|
+
...(signal ? { signal } : {}),
|
|
64
|
+
});
|
|
65
|
+
const summary = response.content.trim();
|
|
66
|
+
if (!summary)
|
|
67
|
+
throw new Error("The model returned an empty summary.");
|
|
68
|
+
// The acknowledgement keeps user/assistant alternation, so the next user turn
|
|
69
|
+
// never follows another user message.
|
|
70
|
+
return {
|
|
71
|
+
messages: [
|
|
72
|
+
{ role: "system", content: systemPrompt },
|
|
73
|
+
{ role: "user", content: `${SUMMARY_PREFIX}\n\n${summary}` },
|
|
74
|
+
{ role: "assistant", content: SUMMARY_ACK },
|
|
75
|
+
],
|
|
76
|
+
summary,
|
|
77
|
+
usage: response.usage,
|
|
78
|
+
};
|
|
79
|
+
}
|
|
80
|
+
//# sourceMappingURL=compact.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"compact.js","sourceRoot":"","sources":["../../src/agent/compact.ts"],"names":[],"mappings":"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"}
|
package/dist/agent/loop.js
CHANGED
|
@@ -127,7 +127,7 @@ export async function* runAgentLoop(messages, opts) {
|
|
|
127
127
|
const toolMsg = {
|
|
128
128
|
role: "tool",
|
|
129
129
|
toolCallId: call.id,
|
|
130
|
-
content: `
|
|
130
|
+
content: `Unknown tool: ${call.function.name}`,
|
|
131
131
|
};
|
|
132
132
|
messages.push(toolMsg);
|
|
133
133
|
await appendSessionMessage(opts.session, toolMsg);
|
|
@@ -141,7 +141,7 @@ export async function* runAgentLoop(messages, opts) {
|
|
|
141
141
|
const toolMsg = {
|
|
142
142
|
role: "tool",
|
|
143
143
|
toolCallId: call.id,
|
|
144
|
-
content: "
|
|
144
|
+
content: "The user denied running this tool.",
|
|
145
145
|
};
|
|
146
146
|
messages.push(toolMsg);
|
|
147
147
|
await appendSessionMessage(opts.session, toolMsg);
|
package/dist/agent/loop.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"loop.js","sourceRoot":"","sources":["../../src/agent/loop.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"loop.js","sourceRoot":"","sources":["../../src/agent/loop.ts"],"names":[],"mappings":"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"}
|
package/dist/agent/tools/edit.js
CHANGED
|
@@ -16,14 +16,14 @@ function countOccurrences(haystack, needle) {
|
|
|
16
16
|
}
|
|
17
17
|
export const editTool = {
|
|
18
18
|
name: "edit",
|
|
19
|
-
description: "
|
|
19
|
+
description: "Replace an exact string in a file with a new string. `oldString` must be unique in the file unless replaceAll=true. Preserves the original line-ending style (CRLF/LF).",
|
|
20
20
|
parameters: {
|
|
21
21
|
type: "object",
|
|
22
22
|
properties: {
|
|
23
|
-
path: { type: "string", description: "
|
|
24
|
-
oldString: { type: "string", description: "
|
|
25
|
-
newString: { type: "string", description: "
|
|
26
|
-
replaceAll: { type: "boolean", description: "
|
|
23
|
+
path: { type: "string", description: "Path to the file." },
|
|
24
|
+
oldString: { type: "string", description: "Exact text to replace (with enough context to be unique)." },
|
|
25
|
+
newString: { type: "string", description: "Replacement text." },
|
|
26
|
+
replaceAll: { type: "boolean", description: "Replace all occurrences instead of requiring uniqueness." },
|
|
27
27
|
},
|
|
28
28
|
required: ["path", "oldString", "newString"],
|
|
29
29
|
},
|
|
@@ -36,14 +36,14 @@ export const editTool = {
|
|
|
36
36
|
const replaceAll = Boolean(args["replaceAll"]);
|
|
37
37
|
const resolved = path.resolve(ctx.cwd, filePath);
|
|
38
38
|
if (oldString === newString) {
|
|
39
|
-
return { output: "oldString
|
|
39
|
+
return { output: "oldString and newString are identical — nothing to change.", isError: true };
|
|
40
40
|
}
|
|
41
41
|
let raw;
|
|
42
42
|
try {
|
|
43
43
|
raw = await readFile(resolved, "utf8");
|
|
44
44
|
}
|
|
45
45
|
catch (err) {
|
|
46
|
-
return { output: `
|
|
46
|
+
return { output: `Error reading ${resolved}: ${err.message}`, isError: true };
|
|
47
47
|
}
|
|
48
48
|
const eol = raw.includes("\r\n") ? "\r\n" : "\n";
|
|
49
49
|
const normalized = raw.replace(/\r\n/g, "\n");
|
|
@@ -51,11 +51,11 @@ export const editTool = {
|
|
|
51
51
|
const replacement = newString.replace(/\r\n/g, "\n");
|
|
52
52
|
const occurrences = countOccurrences(normalized, needle);
|
|
53
53
|
if (occurrences === 0) {
|
|
54
|
-
return { output: `oldString
|
|
54
|
+
return { output: `oldString not found in ${filePath}.`, isError: true };
|
|
55
55
|
}
|
|
56
56
|
if (occurrences > 1 && !replaceAll) {
|
|
57
57
|
return {
|
|
58
|
-
output: `oldString
|
|
58
|
+
output: `oldString appears ${occurrences} times in ${filePath} — add more context to make it unique, or pass replaceAll=true.`,
|
|
59
59
|
isError: true,
|
|
60
60
|
};
|
|
61
61
|
}
|
|
@@ -67,10 +67,10 @@ export const editTool = {
|
|
|
67
67
|
await writeFile(resolved, finalContent, "utf8");
|
|
68
68
|
}
|
|
69
69
|
catch (err) {
|
|
70
|
-
return { output: `
|
|
70
|
+
return { output: `Error writing ${resolved}: ${err.message}`, isError: true };
|
|
71
71
|
}
|
|
72
72
|
return {
|
|
73
|
-
output: `
|
|
73
|
+
output: `Edited ${filePath} (${occurrences} ${occurrences === 1 ? "replacement" : "replacements"}).`,
|
|
74
74
|
isError: false,
|
|
75
75
|
};
|
|
76
76
|
},
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"edit.js","sourceRoot":"","sources":["../../../src/agent/tools/edit.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,SAAS,EAAE,MAAM,kBAAkB,CAAC;AACvD,OAAO,IAAI,MAAM,WAAW,CAAC;AAG7B,SAAS,gBAAgB,CAAC,QAAgB,EAAE,MAAc;IACxD,IAAI,MAAM,CAAC,MAAM,KAAK,CAAC;QAAE,OAAO,CAAC,CAAC;IAClC,IAAI,KAAK,GAAG,CAAC,CAAC;IACd,IAAI,GAAG,GAAG,CAAC,CAAC;IACZ,SAAS,CAAC;QACR,GAAG,GAAG,QAAQ,CAAC,OAAO,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;QACpC,IAAI,GAAG,KAAK,CAAC,CAAC;YAAE,MAAM;QACtB,KAAK,EAAE,CAAC;QACR,GAAG,IAAI,MAAM,CAAC,MAAM,CAAC;IACvB,CAAC;IACD,OAAO,KAAK,CAAC;AACf,CAAC;AAED,MAAM,CAAC,MAAM,QAAQ,GAAmB;IACtC,IAAI,EAAE,MAAM;IACZ,WAAW,EACT,
|
|
1
|
+
{"version":3,"file":"edit.js","sourceRoot":"","sources":["../../../src/agent/tools/edit.ts"],"names":[],"mappings":"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"}
|
|
@@ -2,14 +2,19 @@ import { execFile } from "node:child_process";
|
|
|
2
2
|
import { promisify } from "node:util";
|
|
3
3
|
const execFileAsync = promisify(execFile);
|
|
4
4
|
const MAX_OUTPUT_CHARS = 30_000;
|
|
5
|
+
// Tandem's own session logs and pasted images live under .tandem/ in the working
|
|
6
|
+
// directory. They are not part of the user's change, and in repos that don't
|
|
7
|
+
// ignore .tandem they would show up as untracked files in every diff.
|
|
8
|
+
// `**/` also covers a .tandem in a subdirectory that Tandem was started from earlier.
|
|
9
|
+
const SELF_PATHSPECS = [":(exclude,glob)**/.tandem/sessions/**", ":(exclude,glob)**/.tandem/tmp/**"];
|
|
5
10
|
export const gitDiffTool = {
|
|
6
11
|
name: "git_diff",
|
|
7
|
-
description: "
|
|
12
|
+
description: "Show the git diff for the working directory (unstaged changes), optionally for a single path.",
|
|
8
13
|
parameters: {
|
|
9
14
|
type: "object",
|
|
10
15
|
properties: {
|
|
11
|
-
path: { type: "string", description: "
|
|
12
|
-
staged: { type: "boolean", description: "
|
|
16
|
+
path: { type: "string", description: "Limit the diff to this path." },
|
|
17
|
+
staged: { type: "boolean", description: "Show staged changes (--cached) instead of the working tree." },
|
|
13
18
|
},
|
|
14
19
|
required: [],
|
|
15
20
|
},
|
|
@@ -17,25 +22,43 @@ export const gitDiffTool = {
|
|
|
17
22
|
async execute(args, ctx) {
|
|
18
23
|
const staged = Boolean(args["staged"]);
|
|
19
24
|
const scopePath = args["path"] ? String(args["path"]) : undefined;
|
|
20
|
-
const
|
|
21
|
-
|
|
22
|
-
// --intent-to-add ih markira u indeksu bez stage-ovanja sadržaja, pa se
|
|
23
|
-
// pojave u diff-u kao dodati fajlovi — bezopasno i reverzibilno.
|
|
24
|
-
try {
|
|
25
|
-
await execFileAsync("git", ["add", "--intent-to-add", "--all", ...(scopePath ? ["--", scopePath] : [])], {
|
|
26
|
-
cwd: ctx.cwd,
|
|
27
|
-
});
|
|
28
|
-
}
|
|
29
|
-
catch {
|
|
30
|
-
// Nije git repo ili git nije dostupan — poziv ispod će to jasno prijaviti.
|
|
31
|
-
}
|
|
25
|
+
const pathspecs = ["--", ...(scopePath ? [scopePath] : []), ...SELF_PATHSPECS];
|
|
26
|
+
const gitArgs = ["diff", ...(staged ? ["--cached"] : []), ...pathspecs];
|
|
32
27
|
try {
|
|
33
28
|
const { stdout } = await execFileAsync("git", gitArgs, { cwd: ctx.cwd, maxBuffer: 10 * 1024 * 1024 });
|
|
34
|
-
|
|
35
|
-
|
|
29
|
+
if (staged) {
|
|
30
|
+
const output = stdout.length > MAX_OUTPUT_CHARS ? stdout.slice(0, MAX_OUTPUT_CHARS) + "\n... (truncated)" : stdout;
|
|
31
|
+
return { output: output.trim() || "(no changes)", isError: false };
|
|
32
|
+
}
|
|
33
|
+
const { stdout: untracked } = await execFileAsync("git", ["ls-files", "--others", "--exclude-standard", "-z", ...pathspecs], { cwd: ctx.cwd });
|
|
34
|
+
const files = untracked.split("\0").filter(Boolean);
|
|
35
|
+
const untrackedDiffs = new Array(files.length).fill("");
|
|
36
|
+
let nextFile = 0;
|
|
37
|
+
const worker = async () => {
|
|
38
|
+
while (nextFile < files.length) {
|
|
39
|
+
const index = nextFile++;
|
|
40
|
+
const file = files[index];
|
|
41
|
+
if (!file) {
|
|
42
|
+
continue;
|
|
43
|
+
}
|
|
44
|
+
try {
|
|
45
|
+
await execFileAsync("git", ["diff", "--no-index", "--", "/dev/null", file], {
|
|
46
|
+
cwd: ctx.cwd,
|
|
47
|
+
maxBuffer: 10 * 1024 * 1024,
|
|
48
|
+
});
|
|
49
|
+
}
|
|
50
|
+
catch (err) {
|
|
51
|
+
untrackedDiffs[index] = err.stdout ?? "";
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
};
|
|
55
|
+
await Promise.all(Array.from({ length: Math.min(8, files.length) }, () => worker()));
|
|
56
|
+
const output = [stdout, ...untrackedDiffs].join("");
|
|
57
|
+
const truncated = output.length > MAX_OUTPUT_CHARS ? output.slice(0, MAX_OUTPUT_CHARS) + "\n... (truncated)" : output;
|
|
58
|
+
return { output: truncated.trim() || "(no changes)", isError: false };
|
|
36
59
|
}
|
|
37
60
|
catch (err) {
|
|
38
|
-
return { output: `
|
|
61
|
+
return { output: `git diff error: ${err.message}`, isError: true };
|
|
39
62
|
}
|
|
40
63
|
},
|
|
41
64
|
};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"gitDiff.js","sourceRoot":"","sources":["../../../src/agent/tools/gitDiff.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAC;AAC9C,OAAO,EAAE,SAAS,EAAE,MAAM,WAAW,CAAC;AAGtC,MAAM,aAAa,GAAG,SAAS,CAAC,QAAQ,CAAC,CAAC;AAC1C,MAAM,gBAAgB,GAAG,MAAM,CAAC;AAEhC,MAAM,CAAC,MAAM,WAAW,GAAmB;IACzC,IAAI,EAAE,UAAU;IAChB,WAAW,EAAE
|
|
1
|
+
{"version":3,"file":"gitDiff.js","sourceRoot":"","sources":["../../../src/agent/tools/gitDiff.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAC;AAC9C,OAAO,EAAE,SAAS,EAAE,MAAM,WAAW,CAAC;AAGtC,MAAM,aAAa,GAAG,SAAS,CAAC,QAAQ,CAAC,CAAC;AAC1C,MAAM,gBAAgB,GAAG,MAAM,CAAC;AAEhC,iFAAiF;AACjF,6EAA6E;AAC7E,sEAAsE;AACtE,sFAAsF;AACtF,MAAM,cAAc,GAAG,CAAC,uCAAuC,EAAE,kCAAkC,CAAC,CAAC;AAErG,MAAM,CAAC,MAAM,WAAW,GAAmB;IACzC,IAAI,EAAE,UAAU;IAChB,WAAW,EAAE,+FAA+F;IAC5G,UAAU,EAAE;QACV,IAAI,EAAE,QAAQ;QACd,UAAU,EAAE;YACV,IAAI,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,8BAA8B,EAAE;YACrE,MAAM,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,WAAW,EAAE,6DAA6D,EAAE;SACxG;QACD,QAAQ,EAAE,EAAE;KACb;IACD,aAAa,EAAE,GAAG,EAAE,CAAC,KAAK;IAC1B,KAAK,CAAC,OAAO,CAAC,IAAI,EAAE,GAAG;QACrB,MAAM,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC,CAAC;QACvC,MAAM,SAAS,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;QAClE,MAAM,SAAS,GAAG,CAAC,IAAI,EAAE,GAAG,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,GAAG,cAAc,CAAC,CAAC;QAC/E,MAAM,OAAO,GAAG,CAAC,MAAM,EAAE,GAAG,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,GAAG,SAAS,CAAC,CAAC;QAExE,IAAI,CAAC;YACH,MAAM,EAAE,MAAM,EAAE,GAAG,MAAM,aAAa,CAAC,KAAK,EAAE,OAAO,EAAE,EAAE,GAAG,EAAE,GAAG,CAAC,GAAG,EAAE,SAAS,EAAE,EAAE,GAAG,IAAI,GAAG,IAAI,EAAE,CAAC,CAAC;YACtG,IAAI,MAAM,EAAE,CAAC;gBACX,MAAM,MAAM,GAAG,MAAM,CAAC,MAAM,GAAG,gBAAgB,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,EAAE,gBAAgB,CAAC,GAAG,mBAAmB,CAAC,CAAC,CAAC,MAAM,CAAC;gBACnH,OAAO,EAAE,MAAM,EAAE,MAAM,CAAC,IAAI,EAAE,IAAI,cAAc,EAAE,OAAO,EAAE,KAAK,EAAE,CAAC;YACrE,CAAC;YAED,MAAM,EAAE,MAAM,EAAE,SAAS,EAAE,GAAG,MAAM,aAAa,CAC/C,KAAK,EACL,CAAC,UAAU,EAAE,UAAU,EAAE,oBAAoB,EAAE,IAAI,EAAE,GAAG,SAAS,CAAC,EAClE,EAAE,GAAG,EAAE,GAAG,CAAC,GAAG,EAAE,CACjB,CAAC;YACF,MAAM,KAAK,GAAG,SAAS,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC;YACpD,MAAM,cAAc,GAAG,IAAI,KAAK,CAAS,KAAK,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;YAChE,IAAI,QAAQ,GAAG,CAAC,CAAC;YACjB,MAAM,MAAM,GAAG,KAAK,IAAI,EAAE;gBACxB,OAAO,QAAQ,GAAG,KAAK,CAAC,MAAM,EAAE,CAAC;oBAC/B,MAAM,KAAK,GAAG,QAAQ,EAAE,CAAC;oBACzB,MAAM,IAAI,GAAG,KAAK,CAAC,KAAK,CAAC,CAAC;oBAC1B,IAAI,CAAC,IAAI,EAAE,CAAC;wBACV,SAAS;oBACX,CAAC;oBACD,IAAI,CAAC;wBACH,MAAM,aAAa,CAAC,KAAK,EAAE,CAAC,MAAM,EAAE,YAAY,EAAE,IAAI,EAAE,WAAW,EAAE,IAAI,CAAC,EAAE;4BAC1E,GAAG,EAAE,GAAG,CAAC,GAAG;4BACZ,SAAS,EAAE,EAAE,GAAG,IAAI,GAAG,IAAI;yBAC5B,CAAC,CAAC;oBACL,CAAC;oBAAC,OAAO,GAAG,EAAE,CAAC;wBACb,cAAc,CAAC,KAAK,CAAC,GAAI,GAA2B,CAAC,MAAM,IAAI,EAAE,CAAC;oBACpE,CAAC;gBACH,CAAC;YACH,CAAC,CAAC;YACF,MAAM,OAAO,CAAC,GAAG,CACf,KAAK,CAAC,IAAI,CAAC,EAAE,MAAM,EAAE,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,KAAK,CAAC,MAAM,CAAC,EAAE,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAClE,CAAC;YACF,MAAM,MAAM,GAAG,CAAC,MAAM,EAAE,GAAG,cAAc,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;YACpD,MAAM,SAAS,GAAG,MAAM,CAAC,MAAM,GAAG,gBAAgB,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,EAAE,gBAAgB,CAAC,GAAG,mBAAmB,CAAC,CAAC,CAAC,MAAM,CAAC;YACtH,OAAO,EAAE,MAAM,EAAE,SAAS,CAAC,IAAI,EAAE,IAAI,cAAc,EAAE,OAAO,EAAE,KAAK,EAAE,CAAC;QACxE,CAAC;QAAC,OAAO,GAAG,EAAE,CAAC;YACb,OAAO,EAAE,MAAM,EAAE,mBAAoB,GAAa,CAAC,OAAO,EAAE,EAAE,OAAO,EAAE,IAAI,EAAE,CAAC;QAChF,CAAC;IACH,CAAC;CACF,CAAC"}
|
|
@@ -2,11 +2,11 @@ import { readdir } from "node:fs/promises";
|
|
|
2
2
|
import path from "node:path";
|
|
3
3
|
export const listDirTool = {
|
|
4
4
|
name: "list_dir",
|
|
5
|
-
description: "
|
|
5
|
+
description: "List the contents of a directory (non-recursive).",
|
|
6
6
|
parameters: {
|
|
7
7
|
type: "object",
|
|
8
8
|
properties: {
|
|
9
|
-
path: { type: "string", description: "
|
|
9
|
+
path: { type: "string", description: "Path to the directory. Defaults to the working directory." },
|
|
10
10
|
},
|
|
11
11
|
required: [],
|
|
12
12
|
},
|
|
@@ -19,10 +19,10 @@ export const listDirTool = {
|
|
|
19
19
|
const lines = entries
|
|
20
20
|
.map((e) => `${e.isDirectory() ? "d" : "-"} ${e.name}`)
|
|
21
21
|
.sort();
|
|
22
|
-
return { output: lines.join("\n") || "(
|
|
22
|
+
return { output: lines.join("\n") || "(empty)", isError: false };
|
|
23
23
|
}
|
|
24
24
|
catch (err) {
|
|
25
|
-
return { output: `
|
|
25
|
+
return { output: `Error listing ${resolved}: ${err.message}`, isError: true };
|
|
26
26
|
}
|
|
27
27
|
},
|
|
28
28
|
};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"listDir.js","sourceRoot":"","sources":["../../../src/agent/tools/listDir.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,kBAAkB,CAAC;AAC3C,OAAO,IAAI,MAAM,WAAW,CAAC;AAG7B,MAAM,CAAC,MAAM,WAAW,GAAmB;IACzC,IAAI,EAAE,UAAU;IAChB,WAAW,EAAE,
|
|
1
|
+
{"version":3,"file":"listDir.js","sourceRoot":"","sources":["../../../src/agent/tools/listDir.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,kBAAkB,CAAC;AAC3C,OAAO,IAAI,MAAM,WAAW,CAAC;AAG7B,MAAM,CAAC,MAAM,WAAW,GAAmB;IACzC,IAAI,EAAE,UAAU;IAChB,WAAW,EAAE,mDAAmD;IAChE,UAAU,EAAE;QACV,IAAI,EAAE,QAAQ;QACd,UAAU,EAAE;YACV,IAAI,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,2DAA2D,EAAE;SACnG;QACD,QAAQ,EAAE,EAAE;KACb;IACD,aAAa,EAAE,GAAG,EAAE,CAAC,KAAK;IAC1B,KAAK,CAAC,OAAO,CAAC,IAAI,EAAE,GAAG;QACrB,MAAM,OAAO,GAAG,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC,IAAI,GAAG,CAAC,CAAC;QAC5C,MAAM,QAAQ,GAAG,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,GAAG,EAAE,OAAO,CAAC,CAAC;QAEhD,IAAI,CAAC;YACH,MAAM,OAAO,GAAG,MAAM,OAAO,CAAC,QAAQ,EAAE,EAAE,aAAa,EAAE,IAAI,EAAE,CAAC,CAAC;YACjE,MAAM,KAAK,GAAG,OAAO;iBAClB,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,GAAG,CAAC,CAAC,WAAW,EAAE,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,IAAI,EAAE,CAAC;iBACtD,IAAI,EAAE,CAAC;YACV,OAAO,EAAE,MAAM,EAAE,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,SAAS,EAAE,OAAO,EAAE,KAAK,EAAE,CAAC;QACnE,CAAC;QAAC,OAAO,GAAG,EAAE,CAAC;YACb,OAAO,EAAE,MAAM,EAAE,iBAAiB,QAAQ,KAAM,GAAa,CAAC,OAAO,EAAE,EAAE,OAAO,EAAE,IAAI,EAAE,CAAC;QAC3F,CAAC;IACH,CAAC;CACF,CAAC"}
|
|
@@ -4,13 +4,13 @@ const MAX_LINES = 2000;
|
|
|
4
4
|
const MAX_FILE_BYTES = 10 * 1024 * 1024;
|
|
5
5
|
export const readFileTool = {
|
|
6
6
|
name: "read_file",
|
|
7
|
-
description: "
|
|
7
|
+
description: "Read a file's contents with line numbers (cat -n style). The path may be relative to the working directory.",
|
|
8
8
|
parameters: {
|
|
9
9
|
type: "object",
|
|
10
10
|
properties: {
|
|
11
|
-
path: { type: "string", description: "
|
|
12
|
-
offset: { type: "integer", description: "
|
|
13
|
-
limit: { type: "integer", description: `
|
|
11
|
+
path: { type: "string", description: "Path to the file." },
|
|
12
|
+
offset: { type: "integer", description: "Line to start from (1-indexed). Defaults to 1." },
|
|
13
|
+
limit: { type: "integer", description: `Maximum number of lines to read. Defaults to ${MAX_LINES}.` },
|
|
14
14
|
},
|
|
15
15
|
required: ["path"],
|
|
16
16
|
},
|
|
@@ -24,7 +24,7 @@ export const readFileTool = {
|
|
|
24
24
|
const stats = await stat(resolved);
|
|
25
25
|
if (stats.size > MAX_FILE_BYTES) {
|
|
26
26
|
return {
|
|
27
|
-
output: `
|
|
27
|
+
output: `File is too large to read (${stats.size} bytes, limit ${MAX_FILE_BYTES}). It is probably not a text source file (e.g. a state/binary/vendored file) — check the path or use the shell tool with limited output.`,
|
|
28
28
|
isError: true,
|
|
29
29
|
};
|
|
30
30
|
}
|
|
@@ -36,12 +36,12 @@ export const readFileTool = {
|
|
|
36
36
|
.join("\n");
|
|
37
37
|
const truncated = offset - 1 + limit < lines.length;
|
|
38
38
|
return {
|
|
39
|
-
output: numbered + (truncated ? `\n... (
|
|
39
|
+
output: numbered + (truncated ? `\n... (truncated, ${lines.length} lines total)` : ""),
|
|
40
40
|
isError: false,
|
|
41
41
|
};
|
|
42
42
|
}
|
|
43
43
|
catch (err) {
|
|
44
|
-
return { output: `
|
|
44
|
+
return { output: `Error reading ${resolved}: ${err.message}`, isError: true };
|
|
45
45
|
}
|
|
46
46
|
},
|
|
47
47
|
};
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"readFile.js","sourceRoot":"","sources":["../../../src/agent/tools/readFile.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,IAAI,EAAE,MAAM,kBAAkB,CAAC;AAClD,OAAO,IAAI,MAAM,WAAW,CAAC;AAG7B,MAAM,SAAS,GAAG,IAAI,CAAC;AACvB,MAAM,cAAc,GAAG,EAAE,GAAG,IAAI,GAAG,IAAI,CAAC;AAExC,MAAM,CAAC,MAAM,YAAY,GAAmB;IAC1C,IAAI,EAAE,WAAW;IACjB,WAAW,EACT,
|
|
1
|
+
{"version":3,"file":"readFile.js","sourceRoot":"","sources":["../../../src/agent/tools/readFile.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,IAAI,EAAE,MAAM,kBAAkB,CAAC;AAClD,OAAO,IAAI,MAAM,WAAW,CAAC;AAG7B,MAAM,SAAS,GAAG,IAAI,CAAC;AACvB,MAAM,cAAc,GAAG,EAAE,GAAG,IAAI,GAAG,IAAI,CAAC;AAExC,MAAM,CAAC,MAAM,YAAY,GAAmB;IAC1C,IAAI,EAAE,WAAW;IACjB,WAAW,EACT,6GAA6G;IAC/G,UAAU,EAAE;QACV,IAAI,EAAE,QAAQ;QACd,UAAU,EAAE;YACV,IAAI,EAAE,EAAE,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,mBAAmB,EAAE;YAC1D,MAAM,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,WAAW,EAAE,gDAAgD,EAAE;YAC1F,KAAK,EAAE,EAAE,IAAI,EAAE,SAAS,EAAE,WAAW,EAAE,gDAAgD,SAAS,GAAG,EAAE;SACtG;QACD,QAAQ,EAAE,CAAC,MAAM,CAAC;KACnB;IACD,aAAa,EAAE,GAAG,EAAE,CAAC,KAAK;IAC1B,KAAK,CAAC,OAAO,CAAC,IAAI,EAAE,GAAG;QACrB,MAAM,QAAQ,GAAG,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC,IAAI,EAAE,CAAC,CAAC;QAC5C,MAAM,MAAM,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QACxD,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,MAAM,CAAC,IAAI,CAAC,OAAO,CAAC,IAAI,SAAS,CAAC,CAAC,CAAC;QAC9D,MAAM,QAAQ,GAAG,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,GAAG,EAAE,QAAQ,CAAC,CAAC;QAEjD,IAAI,CAAC;YACH,MAAM,KAAK,GAAG,MAAM,IAAI,CAAC,QAAQ,CAAC,CAAC;YACnC,IAAI,KAAK,CAAC,IAAI,GAAG,cAAc,EAAE,CAAC;gBAChC,OAAO;oBACL,MAAM,EAAE,8BAA8B,KAAK,CAAC,IAAI,iBAAiB,cAAc,0IAA0I;oBACzN,OAAO,EAAE,IAAI;iBACd,CAAC;YACJ,CAAC;YACD,MAAM,GAAG,GAAG,MAAM,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC,CAAC;YAC7C,MAAM,KAAK,GAAG,GAAG,CAAC,KAAK,CAAC,SAAS,CAAC,CAAC;YACnC,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,CAAC,MAAM,GAAG,CAAC,EAAE,MAAM,GAAG,CAAC,GAAG,KAAK,CAAC,CAAC;YAC1D,MAAM,QAAQ,GAAG,KAAK;iBACnB,GAAG,CAAC,CAAC,IAAI,EAAE,CAAC,EAAE,EAAE,CAAC,GAAG,MAAM,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,EAAE,GAAG,CAAC,KAAK,IAAI,EAAE,CAAC;iBACnE,IAAI,CAAC,IAAI,CAAC,CAAC;YACd,MAAM,SAAS,GAAG,MAAM,GAAG,CAAC,GAAG,KAAK,GAAG,KAAK,CAAC,MAAM,CAAC;YACpD,OAAO;gBACL,MAAM,EAAE,QAAQ,GAAG,CAAC,SAAS,CAAC,CAAC,CAAC,qBAAqB,KAAK,CAAC,MAAM,eAAe,CAAC,CAAC,CAAC,EAAE,CAAC;gBACtF,OAAO,EAAE,KAAK;aACf,CAAC;QACJ,CAAC;QAAC,OAAO,GAAG,EAAE,CAAC;YACb,OAAO,EAAE,MAAM,EAAE,iBAAiB,QAAQ,KAAM,GAAa,CAAC,OAAO,EAAE,EAAE,OAAO,EAAE,IAAI,EAAE,CAAC;QAC3F,CAAC;IACH,CAAC;CACF,CAAC"}
|