terse-sdk 0.1.53 → 0.1.55

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.
Files changed (62) hide show
  1. package/README.md +22 -26
  2. package/dist/memoryfs/file.d.ts +16 -0
  3. package/dist/memoryfs/file.d.ts.map +1 -0
  4. package/dist/memoryfs/file.js +40 -0
  5. package/dist/memoryfs/file.js.map +1 -0
  6. package/dist/memoryfs/index.d.ts +25 -0
  7. package/dist/memoryfs/index.d.ts.map +1 -0
  8. package/dist/memoryfs/index.js +60 -0
  9. package/dist/memoryfs/index.js.map +1 -0
  10. package/dist/memoryfs/memory.d.ts +21 -0
  11. package/dist/memoryfs/memory.d.ts.map +1 -0
  12. package/dist/memoryfs/memory.js +196 -0
  13. package/dist/memoryfs/memory.js.map +1 -0
  14. package/dist/memoryfs/paths.d.ts +7 -0
  15. package/dist/memoryfs/paths.d.ts.map +1 -0
  16. package/dist/memoryfs/paths.js +39 -0
  17. package/dist/memoryfs/paths.js.map +1 -0
  18. package/dist/memoryfs/store.d.ts +18 -0
  19. package/dist/memoryfs/store.d.ts.map +1 -0
  20. package/dist/memoryfs/store.js +89 -0
  21. package/dist/memoryfs/store.js.map +1 -0
  22. package/dist/perf.d.ts +9 -0
  23. package/dist/perf.d.ts.map +1 -0
  24. package/dist/perf.js +57 -0
  25. package/dist/perf.js.map +1 -0
  26. package/dist/shared/ApiRoutes.d.ts +348 -0
  27. package/dist/shared/ApiRoutes.d.ts.map +1 -0
  28. package/dist/shared/ApiRoutes.js +325 -0
  29. package/dist/shared/ApiRoutes.js.map +1 -0
  30. package/dist/shared/Configs.d.ts +488 -0
  31. package/dist/shared/Configs.d.ts.map +1 -0
  32. package/dist/shared/Configs.js +785 -0
  33. package/dist/shared/Configs.js.map +1 -0
  34. package/dist/shared/Entities.d.ts +8 -0
  35. package/dist/shared/Entities.d.ts.map +1 -0
  36. package/dist/shared/Entities.js +9 -0
  37. package/dist/shared/Entities.js.map +1 -0
  38. package/dist/shared/Integrations.d.ts +235 -0
  39. package/dist/shared/Integrations.d.ts.map +1 -0
  40. package/dist/shared/Integrations.js +143 -0
  41. package/dist/shared/Integrations.js.map +1 -0
  42. package/dist/shared/ModelEvents.d.ts +176 -0
  43. package/dist/shared/ModelEvents.d.ts.map +1 -0
  44. package/dist/shared/ModelEvents.js +29 -0
  45. package/dist/shared/ModelEvents.js.map +1 -0
  46. package/dist/shared/RunHistoryTypes.d.ts +95 -0
  47. package/dist/shared/RunHistoryTypes.d.ts.map +1 -0
  48. package/dist/shared/RunHistoryTypes.js +11 -0
  49. package/dist/shared/RunHistoryTypes.js.map +1 -0
  50. package/dist/shared/Survey.d.ts +10 -0
  51. package/dist/shared/Survey.d.ts.map +1 -0
  52. package/dist/shared/Survey.js +2 -0
  53. package/dist/shared/Survey.js.map +1 -0
  54. package/dist/shared/TicketSystem.d.ts +154 -0
  55. package/dist/shared/TicketSystem.d.ts.map +1 -0
  56. package/dist/shared/TicketSystem.js +21 -0
  57. package/dist/shared/TicketSystem.js.map +1 -0
  58. package/dist/shared/types.d.ts +1732 -0
  59. package/dist/shared/types.d.ts.map +1 -0
  60. package/dist/shared/types.js +17 -0
  61. package/dist/shared/types.js.map +1 -0
  62. package/package.json +2 -2
package/README.md CHANGED
@@ -19,27 +19,16 @@ The fastest way to get started is `npm install -g terse-cli && terse init my-pro
19
19
  A Terse workflow is a single TypeScript file. The job below watches a repo for new pull requests, posts a deterministic Slack message, then threads an agent-written summary under it:
20
20
 
21
21
  ```ts
22
- import { GithubPRTrigger, TerseAgent, createJob } from "terse-sdk"
23
- import { Repos, Skills, SlackChannel, Triggers } from "../terse.generated"
22
+ import { GithubPRTrigger, generateText, createJob } from "terse-sdk"
23
+ import { Repos, Skills, SlackChannel, Triggers, toolbox } from "../terse.generated"
24
24
  // ^^ Generated based on your workspace
25
25
 
26
26
  createJob({
27
27
  name: "Summarize PR and send slack message",
28
28
  triggers: [Triggers.github.onPROpened({ repo: Repos.TerseAI.Terse })],
29
29
  onTrigger: async (event: GithubPRTrigger) => {
30
- // Create durable Agents
31
- const prompt = "Summarize the incoming PR and send to slack. Format the summary in Block Kit; include screenshots or diagrams from the PR as image blocks."
32
- const agent = TerseAgent.create({
33
- prompt,
34
- skills: [
35
- // Fine tune what agents have access to. Impossible to modify anything outside of this scope
36
- Skills.github({ repos: [Repos.TerseAI.Terse] }),
37
- Skills.slack({ channel: SlackChannel.AllTerseInc })
38
- ]
39
- })
40
-
41
- // deterministically call a tool
42
- const message = await agent.tools.slack.sendMessage({
30
+ // Deterministic call — fixed channel, fixed message. No agent needed.
31
+ const message = await toolbox.slack.sendMessage({
43
32
  channelId: SlackChannel.AllTerseInc.channelId,
44
33
  message: "New PR from " + event.sender.login + "!"
45
34
  })
@@ -47,11 +36,19 @@ createJob({
47
36
  // Outputs are strongly typed
48
37
  const parentId = message.message_ts
49
38
 
50
- // Trigger the Agent with Github + Slack tools auto added
51
- await agent.runAndWait(`
52
- Summarize this PR ${event.formatForAgentRunner()}.
53
- Keep it short. Reply in a thread to the Slack message (thread parent ts: ${parentId}).
54
- `)
39
+ // Agentic: one prompt in, the model uses the GitHub + Slack tools granted via skills
40
+ await generateText({
41
+ prompt: `
42
+ Summarize this PR ${event.formatForAgentRunner()}.
43
+ Keep it short. Format the summary in Block Kit; include screenshots or diagrams from the PR as image blocks.
44
+ Reply in a thread to the Slack message (thread parent ts: ${parentId}).
45
+ `,
46
+ skills: [
47
+ // Fine tune what the agent has access to. Impossible to touch anything outside this scope
48
+ Skills.github({ repos: [Repos.TerseAI.Terse] }),
49
+ Skills.slack({ channel: SlackChannel.AllTerseInc })
50
+ ]
51
+ })
55
52
  }
56
53
  })
57
54
  ```
@@ -61,14 +58,13 @@ createJob({
61
58
  | Concept | What it is |
62
59
  |---|---|
63
60
  | `createJob()` | Registers a workflow at module load time. |
64
- | `TerseAgent.create()` | Build an agent inside `onTrigger` with `prompt`, `skills`, and `toolApprovals`. |
65
- | `agent.run()` | Stream the model run as an async iterable. |
66
- | `agent.runAndWait()` | Run to completion. Pass a `zod` schema for structured output. |
67
- | `agent.tools.*` | Generated, deterministic wrappers. Call directly to bypass the LLM. |
61
+ | `generateText()` | The shorthand for agentic runs: one prompt in, final output out. The model can call any tool granted via `skills`. Pass a `zod` `outputSchema` for structured output. Reach for this in almost every job. |
62
+ | `toolbox.*` | Generated, deterministic wrappers. Call directly to bypass the LLM. No agent or `skills` needed. |
68
63
  | `Triggers.*` | Per-integration trigger builders, plus `Triggers.schedule.cron()` and `Triggers.webhook.onRequest<Body>()`. |
69
- | `Skills.*` | Integration skill factories (e.g. `Skills.github({...})`, `Skills.slack({...})`) that scope the tools available to the agent. |
64
+ | `Skills.*` | Integration skill factories (e.g. `Skills.github({...})`, `Skills.slack({...})`) that scope the tools available to the model. |
65
+ | `TerseAgent.create()` | The lower-level agent `generateText` wraps. Use directly only to stream with `run()` or reuse one agent instance across calls. |
70
66
 
71
- The trigger builders, skill constructors, and `agent.tools.*` wrappers come from `src/terse.generated.ts`, which is produced by `terse generate`. Do not edit it by hand.
67
+ The trigger builders, skill constructors, and `toolbox.*` wrappers come from `src/terse.generated.ts`, which is produced by `terse generate`. Do not edit it by hand.
72
68
 
73
69
  Full reference: [docs.useterse.ai/reference/typescript-sdk](https://docs.useterse.ai/reference/typescript-sdk).
74
70
 
@@ -0,0 +1,16 @@
1
+ import type { FsEntry, LocalFsStore } from "./store.js";
2
+ export type FileCommand = "list" | "read" | "write" | "delete";
3
+ export type FileCommandInput = {
4
+ command: FileCommand;
5
+ path?: string | null;
6
+ content?: string | null;
7
+ };
8
+ export type FileCommandResult = {
9
+ success: true;
10
+ message: string;
11
+ entries?: FsEntry[];
12
+ content?: string;
13
+ };
14
+ export declare function executeFileCommand(store: LocalFsStore, input: FileCommandInput): Promise<FileCommandResult>;
15
+ export declare const MUTATING_FILE_COMMANDS: ReadonlySet<FileCommand>;
16
+ //# sourceMappingURL=file.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"file.d.ts","sourceRoot":"","sources":["../../src/memoryfs/file.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,OAAO,EAAE,YAAY,EAAE,MAAM,YAAY,CAAA;AAEvD,MAAM,MAAM,WAAW,GAAG,MAAM,GAAG,MAAM,GAAG,OAAO,GAAG,QAAQ,CAAA;AAE9D,MAAM,MAAM,gBAAgB,GAAG;IAC3B,OAAO,EAAE,WAAW,CAAA;IACpB,IAAI,CAAC,EAAE,MAAM,GAAG,IAAI,CAAA;IACpB,OAAO,CAAC,EAAE,MAAM,GAAG,IAAI,CAAA;CAC1B,CAAA;AAED,MAAM,MAAM,iBAAiB,GAAG;IAC5B,OAAO,EAAE,IAAI,CAAA;IACb,OAAO,EAAE,MAAM,CAAA;IACf,OAAO,CAAC,EAAE,OAAO,EAAE,CAAA;IACnB,OAAO,CAAC,EAAE,MAAM,CAAA;CACnB,CAAA;AAED,wBAAsB,kBAAkB,CAAC,KAAK,EAAE,YAAY,EAAE,KAAK,EAAE,gBAAgB,GAAG,OAAO,CAAC,iBAAiB,CAAC,CAoCjH;AAED,eAAO,MAAM,sBAAsB,EAAE,WAAW,CAAC,WAAW,CAAgC,CAAA"}
@@ -0,0 +1,40 @@
1
+ import { formatHumanSize } from "./paths.js";
2
+ export async function executeFileCommand(store, input) {
3
+ switch (input.command) {
4
+ case "list": {
5
+ const entries = await store.list(input.path ?? "");
6
+ if (entries.length === 0) {
7
+ return { success: true, message: `Directory ${input.path || "/"} is empty.`, entries: [] };
8
+ }
9
+ const listing = entries.map(entry => `${formatHumanSize(entry.sizeBytes)}\t${entry.path}${entry.isDirectory ? "/" : ""}`).join("\n");
10
+ return { success: true, message: `Files in ${input.path || "/"}:\n${listing}`, entries };
11
+ }
12
+ case "read": {
13
+ if (!input.path) {
14
+ throw new Error("read requires path");
15
+ }
16
+ const content = await store.read(input.path);
17
+ return { success: true, message: `Read ${input.path}`, content };
18
+ }
19
+ case "write": {
20
+ if (!input.path || input.content === undefined || input.content === null) {
21
+ throw new Error("write requires path and content");
22
+ }
23
+ await store.write(input.path, input.content);
24
+ return { success: true, message: `Wrote file ${input.path}` };
25
+ }
26
+ case "delete": {
27
+ if (!input.path) {
28
+ throw new Error("delete requires path");
29
+ }
30
+ await store.deletePath(input.path);
31
+ return { success: true, message: `Deleted ${input.path}` };
32
+ }
33
+ default: {
34
+ const exhaustive = input.command;
35
+ throw new Error(`Unsupported file command: ${exhaustive}`);
36
+ }
37
+ }
38
+ }
39
+ export const MUTATING_FILE_COMMANDS = new Set(["write", "delete"]);
40
+ //# sourceMappingURL=file.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"file.js","sourceRoot":"","sources":["../../src/memoryfs/file.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAE,MAAM,YAAY,CAAA;AAkB5C,MAAM,CAAC,KAAK,UAAU,kBAAkB,CAAC,KAAmB,EAAE,KAAuB;IACjF,QAAQ,KAAK,CAAC,OAAO,EAAE,CAAC;QACpB,KAAK,MAAM,CAAC,CAAC,CAAC;YACV,MAAM,OAAO,GAAG,MAAM,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,IAAI,EAAE,CAAC,CAAA;YAClD,IAAI,OAAO,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;gBACvB,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,aAAa,KAAK,CAAC,IAAI,IAAI,GAAG,YAAY,EAAE,OAAO,EAAE,EAAE,EAAE,CAAA;YAC9F,CAAC;YACD,MAAM,OAAO,GAAG,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,EAAE,CAAC,GAAG,eAAe,CAAC,KAAK,CAAC,SAAS,CAAC,KAAK,KAAK,CAAC,IAAI,GAAG,KAAK,CAAC,WAAW,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAA;YACpI,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,YAAY,KAAK,CAAC,IAAI,IAAI,GAAG,MAAM,OAAO,EAAE,EAAE,OAAO,EAAE,CAAA;QAC5F,CAAC;QACD,KAAK,MAAM,CAAC,CAAC,CAAC;YACV,IAAI,CAAC,KAAK,CAAC,IAAI,EAAE,CAAC;gBACd,MAAM,IAAI,KAAK,CAAC,oBAAoB,CAAC,CAAA;YACzC,CAAC;YACD,MAAM,OAAO,GAAG,MAAM,KAAK,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,CAAA;YAC5C,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,QAAQ,KAAK,CAAC,IAAI,EAAE,EAAE,OAAO,EAAE,CAAA;QACpE,CAAC;QACD,KAAK,OAAO,CAAC,CAAC,CAAC;YACX,IAAI,CAAC,KAAK,CAAC,IAAI,IAAI,KAAK,CAAC,OAAO,KAAK,SAAS,IAAI,KAAK,CAAC,OAAO,KAAK,IAAI,EAAE,CAAC;gBACvE,MAAM,IAAI,KAAK,CAAC,iCAAiC,CAAC,CAAA;YACtD,CAAC;YACD,MAAM,KAAK,CAAC,KAAK,CAAC,KAAK,CAAC,IAAI,EAAE,KAAK,CAAC,OAAO,CAAC,CAAA;YAC5C,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,cAAc,KAAK,CAAC,IAAI,EAAE,EAAE,CAAA;QACjE,CAAC;QACD,KAAK,QAAQ,CAAC,CAAC,CAAC;YACZ,IAAI,CAAC,KAAK,CAAC,IAAI,EAAE,CAAC;gBACd,MAAM,IAAI,KAAK,CAAC,sBAAsB,CAAC,CAAA;YAC3C,CAAC;YACD,MAAM,KAAK,CAAC,UAAU,CAAC,KAAK,CAAC,IAAI,CAAC,CAAA;YAClC,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,WAAW,KAAK,CAAC,IAAI,EAAE,EAAE,CAAA;QAC9D,CAAC;QACD,OAAO,CAAC,CAAC,CAAC;YACN,MAAM,UAAU,GAAU,KAAK,CAAC,OAAO,CAAA;YACvC,MAAM,IAAI,KAAK,CAAC,6BAA6B,UAAU,EAAE,CAAC,CAAA;QAC9D,CAAC;IACL,CAAC;AACL,CAAC;AAED,MAAM,CAAC,MAAM,sBAAsB,GAA6B,IAAI,GAAG,CAAC,CAAC,OAAO,EAAE,QAAQ,CAAC,CAAC,CAAA"}
@@ -0,0 +1,25 @@
1
+ import { type FileCommandInput, type FileCommandResult } from "./file.js";
2
+ import { type MemoryCommandInput, type MemoryCommandResult } from "./memory.js";
3
+ export { LocalFsStore } from "./store.js";
4
+ export type { FsEntry } from "./store.js";
5
+ export { executeMemoryCommand, type MemoryCommand, type MemoryCommandInput, type MemoryCommandResult } from "./memory.js";
6
+ export { executeFileCommand, type FileCommand, type FileCommandInput, type FileCommandResult } from "./file.js";
7
+ export { MEMORY_ROOT, resolveFsRoot } from "./paths.js";
8
+ /** Tool names that resolve against the co-located filesystem instead of the backend. */
9
+ export declare const MEMORY_FS_TOOL_NAMES: readonly ["memory", "file"];
10
+ export type MemoryFsToolName = (typeof MEMORY_FS_TOOL_NAMES)[number];
11
+ export declare function isMemoryFsTool(toolName: string): toolName is MemoryFsToolName;
12
+ export type MemoryFsRequest = {
13
+ tool: "memory";
14
+ input: MemoryCommandInput;
15
+ } | {
16
+ tool: "file";
17
+ input: FileCommandInput;
18
+ };
19
+ export type MemoryFsResult = MemoryCommandResult | FileCommandResult;
20
+ /**
21
+ * Single entry point used by both reach-back paths. Resolves the co-located root, runs the
22
+ * command against the local filesystem, and commits the volume after a mutating op.
23
+ */
24
+ export declare function runMemoryFsCommand(request: MemoryFsRequest): Promise<MemoryFsResult>;
25
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/memoryfs/index.ts"],"names":[],"mappings":"AAIA,OAAO,EAAE,KAAK,gBAAgB,EAAE,KAAK,iBAAiB,EAA8C,MAAM,WAAW,CAAA;AACrH,OAAO,EAA4B,KAAK,kBAAkB,EAAE,KAAK,mBAAmB,EAAwB,MAAM,aAAa,CAAA;AAI/H,OAAO,EAAE,YAAY,EAAE,MAAM,YAAY,CAAA;AACzC,YAAY,EAAE,OAAO,EAAE,MAAM,YAAY,CAAA;AACzC,OAAO,EAAE,oBAAoB,EAAE,KAAK,aAAa,EAAE,KAAK,kBAAkB,EAAE,KAAK,mBAAmB,EAAE,MAAM,aAAa,CAAA;AACzH,OAAO,EAAE,kBAAkB,EAAE,KAAK,WAAW,EAAE,KAAK,gBAAgB,EAAE,KAAK,iBAAiB,EAAE,MAAM,WAAW,CAAA;AAC/G,OAAO,EAAE,WAAW,EAAE,aAAa,EAAE,MAAM,YAAY,CAAA;AAEvD,wFAAwF;AACxF,eAAO,MAAM,oBAAoB,6BAA8B,CAAA;AAC/D,MAAM,MAAM,gBAAgB,GAAG,CAAC,OAAO,oBAAoB,CAAC,CAAC,MAAM,CAAC,CAAA;AAEpE,wBAAgB,cAAc,CAAC,QAAQ,EAAE,MAAM,GAAG,QAAQ,IAAI,gBAAgB,CAE7E;AAuBD,MAAM,MAAM,eAAe,GAAG;IAAE,IAAI,EAAE,QAAQ,CAAC;IAAC,KAAK,EAAE,kBAAkB,CAAA;CAAE,GAAG;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,gBAAgB,CAAA;CAAE,CAAA;AAEvH,MAAM,MAAM,cAAc,GAAG,mBAAmB,GAAG,iBAAiB,CAAA;AAEpE;;;GAGG;AACH,wBAAsB,kBAAkB,CAAC,OAAO,EAAE,eAAe,GAAG,OAAO,CAAC,cAAc,CAAC,CAkB1F"}
@@ -0,0 +1,60 @@
1
+ import { execFile } from "node:child_process";
2
+ import path from "node:path";
3
+ import { promisify } from "node:util";
4
+ import { MUTATING_FILE_COMMANDS, executeFileCommand } from "./file.js";
5
+ import { MUTATING_MEMORY_COMMANDS, executeMemoryCommand } from "./memory.js";
6
+ import { FILES_SUBDIR, MEMORY_SUBDIR, resolveFsRoot } from "./paths.js";
7
+ import { LocalFsStore } from "./store.js";
8
+ export { LocalFsStore } from "./store.js";
9
+ export { executeMemoryCommand } from "./memory.js";
10
+ export { executeFileCommand } from "./file.js";
11
+ export { MEMORY_ROOT, resolveFsRoot } from "./paths.js";
12
+ /** Tool names that resolve against the co-located filesystem instead of the backend. */
13
+ export const MEMORY_FS_TOOL_NAMES = ["memory", "file"];
14
+ export function isMemoryFsTool(toolName) {
15
+ return MEMORY_FS_TOOL_NAMES.includes(toolName);
16
+ }
17
+ const execFileAsync = promisify(execFile);
18
+ /**
19
+ * Commit pending writes to the backing Modal volume. On Volumes v2 `sync <mountpoint>`
20
+ * flushes and commits, so changes become visible to other containers. Gated by
21
+ * TERSE_FS_COMMIT (set by the backend only when running on a mounted volume); a no-op for
22
+ * local-dev where writes already live on the dev machine's disk.
23
+ */
24
+ async function commitMount(mountPath) {
25
+ if (process.env.TERSE_FS_COMMIT !== "1")
26
+ return;
27
+ try {
28
+ await execFileAsync("sync", [mountPath]);
29
+ }
30
+ catch {
31
+ try {
32
+ await execFileAsync("sync", []);
33
+ }
34
+ catch {
35
+ // best-effort: fall back to Modal's background commit
36
+ }
37
+ }
38
+ }
39
+ /**
40
+ * Single entry point used by both reach-back paths. Resolves the co-located root, runs the
41
+ * command against the local filesystem, and commits the volume after a mutating op.
42
+ */
43
+ export async function runMemoryFsCommand(request) {
44
+ const root = resolveFsRoot();
45
+ if (request.tool === "memory") {
46
+ const store = new LocalFsStore(path.join(root, MEMORY_SUBDIR));
47
+ const result = await executeMemoryCommand(store, request.input);
48
+ if (MUTATING_MEMORY_COMMANDS.has(request.input.command)) {
49
+ await commitMount(root);
50
+ }
51
+ return result;
52
+ }
53
+ const store = new LocalFsStore(path.join(root, FILES_SUBDIR));
54
+ const result = await executeFileCommand(store, request.input);
55
+ if (MUTATING_FILE_COMMANDS.has(request.input.command)) {
56
+ await commitMount(root);
57
+ }
58
+ return result;
59
+ }
60
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/memoryfs/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAA;AAC7C,OAAO,IAAI,MAAM,WAAW,CAAA;AAC5B,OAAO,EAAE,SAAS,EAAE,MAAM,WAAW,CAAA;AAErC,OAAO,EAAiD,sBAAsB,EAAE,kBAAkB,EAAE,MAAM,WAAW,CAAA;AACrH,OAAO,EAAE,wBAAwB,EAAqD,oBAAoB,EAAE,MAAM,aAAa,CAAA;AAC/H,OAAO,EAAE,YAAY,EAAE,aAAa,EAAE,aAAa,EAAE,MAAM,YAAY,CAAA;AACvE,OAAO,EAAE,YAAY,EAAE,MAAM,YAAY,CAAA;AAEzC,OAAO,EAAE,YAAY,EAAE,MAAM,YAAY,CAAA;AAEzC,OAAO,EAAE,oBAAoB,EAAyE,MAAM,aAAa,CAAA;AACzH,OAAO,EAAE,kBAAkB,EAAmE,MAAM,WAAW,CAAA;AAC/G,OAAO,EAAE,WAAW,EAAE,aAAa,EAAE,MAAM,YAAY,CAAA;AAEvD,wFAAwF;AACxF,MAAM,CAAC,MAAM,oBAAoB,GAAG,CAAC,QAAQ,EAAE,MAAM,CAAU,CAAA;AAG/D,MAAM,UAAU,cAAc,CAAC,QAAgB;IAC3C,OAAQ,oBAA0C,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAA;AACzE,CAAC;AAED,MAAM,aAAa,GAAG,SAAS,CAAC,QAAQ,CAAC,CAAA;AAEzC;;;;;GAKG;AACH,KAAK,UAAU,WAAW,CAAC,SAAiB;IACxC,IAAI,OAAO,CAAC,GAAG,CAAC,eAAe,KAAK,GAAG;QAAE,OAAM;IAC/C,IAAI,CAAC;QACD,MAAM,aAAa,CAAC,MAAM,EAAE,CAAC,SAAS,CAAC,CAAC,CAAA;IAC5C,CAAC;IAAC,MAAM,CAAC;QACL,IAAI,CAAC;YACD,MAAM,aAAa,CAAC,MAAM,EAAE,EAAE,CAAC,CAAA;QACnC,CAAC;QAAC,MAAM,CAAC;YACL,sDAAsD;QAC1D,CAAC;IACL,CAAC;AACL,CAAC;AAMD;;;GAGG;AACH,MAAM,CAAC,KAAK,UAAU,kBAAkB,CAAC,OAAwB;IAC7D,MAAM,IAAI,GAAG,aAAa,EAAE,CAAA;IAE5B,IAAI,OAAO,CAAC,IAAI,KAAK,QAAQ,EAAE,CAAC;QAC5B,MAAM,KAAK,GAAG,IAAI,YAAY,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,aAAa,CAAC,CAAC,CAAA;QAC9D,MAAM,MAAM,GAAG,MAAM,oBAAoB,CAAC,KAAK,EAAE,OAAO,CAAC,KAAK,CAAC,CAAA;QAC/D,IAAI,wBAAwB,CAAC,GAAG,CAAC,OAAO,CAAC,KAAK,CAAC,OAAO,CAAC,EAAE,CAAC;YACtD,MAAM,WAAW,CAAC,IAAI,CAAC,CAAA;QAC3B,CAAC;QACD,OAAO,MAAM,CAAA;IACjB,CAAC;IAED,MAAM,KAAK,GAAG,IAAI,YAAY,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,YAAY,CAAC,CAAC,CAAA;IAC7D,MAAM,MAAM,GAAG,MAAM,kBAAkB,CAAC,KAAK,EAAE,OAAO,CAAC,KAAK,CAAC,CAAA;IAC7D,IAAI,sBAAsB,CAAC,GAAG,CAAC,OAAO,CAAC,KAAK,CAAC,OAAO,CAAC,EAAE,CAAC;QACpD,MAAM,WAAW,CAAC,IAAI,CAAC,CAAA;IAC3B,CAAC;IACD,OAAO,MAAM,CAAA;AACjB,CAAC"}
@@ -0,0 +1,21 @@
1
+ import type { LocalFsStore } from "./store.js";
2
+ export type MemoryCommand = "view" | "create" | "str_replace" | "insert" | "delete" | "rename";
3
+ export type MemoryCommandInput = {
4
+ command: MemoryCommand;
5
+ path?: string;
6
+ view_range?: [number, number] | null;
7
+ file_text?: string;
8
+ old_str?: string;
9
+ new_str?: string;
10
+ insert_line?: number;
11
+ insert_text?: string;
12
+ old_path?: string;
13
+ new_path?: string;
14
+ };
15
+ export type MemoryCommandResult = {
16
+ success: true;
17
+ message: string;
18
+ };
19
+ export declare function executeMemoryCommand(store: LocalFsStore, input: MemoryCommandInput): Promise<MemoryCommandResult>;
20
+ export declare const MUTATING_MEMORY_COMMANDS: ReadonlySet<MemoryCommand>;
21
+ //# sourceMappingURL=memory.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"memory.d.ts","sourceRoot":"","sources":["../../src/memoryfs/memory.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,YAAY,CAAA;AAE9C,MAAM,MAAM,aAAa,GAAG,MAAM,GAAG,QAAQ,GAAG,aAAa,GAAG,QAAQ,GAAG,QAAQ,GAAG,QAAQ,CAAA;AAE9F,MAAM,MAAM,kBAAkB,GAAG;IAC7B,OAAO,EAAE,aAAa,CAAA;IACtB,IAAI,CAAC,EAAE,MAAM,CAAA;IACb,UAAU,CAAC,EAAE,CAAC,MAAM,EAAE,MAAM,CAAC,GAAG,IAAI,CAAA;IACpC,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,OAAO,CAAC,EAAE,MAAM,CAAA;IAChB,OAAO,CAAC,EAAE,MAAM,CAAA;IAChB,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,QAAQ,CAAC,EAAE,MAAM,CAAA;IACjB,QAAQ,CAAC,EAAE,MAAM,CAAA;CACpB,CAAA;AAED,MAAM,MAAM,mBAAmB,GAAG;IAAE,OAAO,EAAE,IAAI,CAAC;IAAC,OAAO,EAAE,MAAM,CAAA;CAAE,CAAA;AAgFpE,wBAAsB,oBAAoB,CAAC,KAAK,EAAE,YAAY,EAAE,KAAK,EAAE,kBAAkB,GAAG,OAAO,CAAC,mBAAmB,CAAC,CAoIvH;AAED,eAAO,MAAM,wBAAwB,EAAE,WAAW,CAAC,aAAa,CAAoE,CAAA"}
@@ -0,0 +1,196 @@
1
+ import { MEMORY_ROOT, formatHumanSize, resolveRelativePath } from "./paths.js";
2
+ function memoryDisplayPath(relativePath) {
3
+ const normalized = relativePath.replace(/^\/+/, "");
4
+ if (!normalized)
5
+ return MEMORY_ROOT;
6
+ return `${MEMORY_ROOT}/${normalized}`;
7
+ }
8
+ function resolveMemoryPath(inputPath) {
9
+ const trimmed = inputPath.trim();
10
+ if (trimmed === MEMORY_ROOT || trimmed === `${MEMORY_ROOT}/`) {
11
+ return "";
12
+ }
13
+ let pathPart = trimmed;
14
+ if (pathPart.startsWith(`${MEMORY_ROOT}/`)) {
15
+ pathPart = pathPart.slice(MEMORY_ROOT.length + 1);
16
+ }
17
+ else if (pathPart.startsWith("/")) {
18
+ pathPart = pathPart.slice(1);
19
+ }
20
+ return resolveRelativePath(pathPart);
21
+ }
22
+ function resolveMemoryPathOptional(inputPath) {
23
+ if (!inputPath || inputPath.trim().length === 0) {
24
+ return "";
25
+ }
26
+ return resolveMemoryPath(inputPath);
27
+ }
28
+ function formatLineNumber(lineNumber) {
29
+ return String(lineNumber).padStart(6, " ");
30
+ }
31
+ async function listDirectoryView(store, relativePath, displayPath) {
32
+ const entries = await store.list(relativePath);
33
+ const lines = [`Here're the files and directories up to 2 levels deep in ${displayPath}, excluding hidden items and node_modules:`];
34
+ const rootStat = relativePath ? await store.stat(relativePath) : null;
35
+ lines.push(`${formatHumanSize(rootStat?.sizeBytes ?? 4096)}\t${displayPath}`);
36
+ for (const entry of entries) {
37
+ lines.push(`${formatHumanSize(entry.sizeBytes)}\t${memoryDisplayPath(entry.path)}`);
38
+ if (entry.isDirectory) {
39
+ const children = await store.list(entry.path);
40
+ for (const child of children) {
41
+ lines.push(`${formatHumanSize(child.sizeBytes)}\t${memoryDisplayPath(child.path)}`);
42
+ }
43
+ }
44
+ }
45
+ return lines.join("\n");
46
+ }
47
+ async function viewFile(store, relativePath, displayPath, viewRange) {
48
+ const content = await store.read(relativePath);
49
+ const lines = content.split("\n");
50
+ if (lines.length > 999_999) {
51
+ return `File ${displayPath} exceeds maximum line limit of 999,999 lines.`;
52
+ }
53
+ const start = viewRange?.[0] ?? 1;
54
+ const end = viewRange?.[1] ?? lines.length;
55
+ const selected = lines.slice(Math.max(start, 1) - 1, end);
56
+ const body = selected.map((line, index) => `${formatLineNumber(start + index)}\t${line}`).join("\n");
57
+ return `Here's the content of ${displayPath} with line numbers:\n${body}`;
58
+ }
59
+ function snippetWithLineNumbers(content, centerLine, radius = 4) {
60
+ const lines = content.split("\n");
61
+ const start = Math.max(centerLine - radius, 1);
62
+ const end = Math.min(centerLine + radius, lines.length);
63
+ return lines
64
+ .slice(start - 1, end)
65
+ .map((line, index) => `${formatLineNumber(start + index)}\t${line}`)
66
+ .join("\n");
67
+ }
68
+ export async function executeMemoryCommand(store, input) {
69
+ switch (input.command) {
70
+ case "view": {
71
+ const relativePath = resolveMemoryPathOptional(input.path);
72
+ const displayPath = memoryDisplayPath(relativePath);
73
+ const exists = relativePath === "" ? true : await store.exists(relativePath);
74
+ if (!exists) {
75
+ return { success: true, message: `The path ${displayPath} does not exist. Please provide a valid path.` };
76
+ }
77
+ const stat = relativePath === "" ? { isDirectory: true } : await store.stat(relativePath);
78
+ if (stat.isDirectory) {
79
+ return { success: true, message: await listDirectoryView(store, relativePath, displayPath) };
80
+ }
81
+ return { success: true, message: await viewFile(store, relativePath, displayPath, input.view_range ?? undefined) };
82
+ }
83
+ case "create": {
84
+ if (!input.path || input.file_text === undefined) {
85
+ throw new Error("create requires path and file_text");
86
+ }
87
+ const relativePath = resolveMemoryPath(input.path);
88
+ const displayPath = memoryDisplayPath(relativePath);
89
+ if (await store.exists(relativePath)) {
90
+ return { success: true, message: `Error: File ${displayPath} already exists` };
91
+ }
92
+ await store.write(relativePath, input.file_text);
93
+ return { success: true, message: `File created successfully at: ${displayPath}` };
94
+ }
95
+ case "str_replace": {
96
+ if (!input.path || input.old_str === undefined || input.new_str === undefined) {
97
+ throw new Error("str_replace requires path, old_str, and new_str");
98
+ }
99
+ const relativePath = resolveMemoryPath(input.path);
100
+ const displayPath = memoryDisplayPath(relativePath);
101
+ if (!(await store.exists(relativePath))) {
102
+ return { success: true, message: `Error: The path ${displayPath} does not exist. Please provide a valid path.` };
103
+ }
104
+ const stat = await store.stat(relativePath);
105
+ if (stat.isDirectory) {
106
+ return { success: true, message: `Error: The path ${displayPath} does not exist. Please provide a valid path.` };
107
+ }
108
+ const content = await store.read(relativePath);
109
+ const occurrences = [];
110
+ let index = content.indexOf(input.old_str);
111
+ while (index !== -1) {
112
+ const lineNumber = content.slice(0, index).split("\n").length;
113
+ occurrences.push(lineNumber);
114
+ index = content.indexOf(input.old_str, index + input.old_str.length);
115
+ }
116
+ if (occurrences.length === 0) {
117
+ return { success: true, message: `No replacement was performed, old_str \`${input.old_str}\` did not appear verbatim in ${displayPath}.` };
118
+ }
119
+ if (occurrences.length > 1) {
120
+ return {
121
+ success: true,
122
+ message: `No replacement was performed. Multiple occurrences of old_str \`${input.old_str}\` in lines: ${occurrences.join(", ")}. Please ensure it is unique`
123
+ };
124
+ }
125
+ const updated = content.replace(input.old_str, input.new_str);
126
+ await store.write(relativePath, updated);
127
+ const editedLine = content.slice(0, content.indexOf(input.old_str)).split("\n").length;
128
+ return {
129
+ success: true,
130
+ message: `The memory file has been edited.\n${snippetWithLineNumbers(updated, editedLine)}`
131
+ };
132
+ }
133
+ case "insert": {
134
+ if (!input.path || input.insert_line === undefined || input.insert_text === undefined) {
135
+ throw new Error("insert requires path, insert_line, and insert_text");
136
+ }
137
+ const relativePath = resolveMemoryPath(input.path);
138
+ const displayPath = memoryDisplayPath(relativePath);
139
+ if (!(await store.exists(relativePath))) {
140
+ return { success: true, message: `Error: The path ${displayPath} does not exist` };
141
+ }
142
+ const stat = await store.stat(relativePath);
143
+ if (stat.isDirectory) {
144
+ return { success: true, message: `Error: The path ${displayPath} does not exist` };
145
+ }
146
+ const content = await store.read(relativePath);
147
+ const lines = content.split("\n");
148
+ const maxLine = lines.length;
149
+ if (input.insert_line < 0 || input.insert_line > maxLine) {
150
+ return {
151
+ success: true,
152
+ message: `Error: Invalid \`insert_line\` parameter: ${input.insert_line}. It should be within the range of lines of the file: [0, ${maxLine}]`
153
+ };
154
+ }
155
+ const insertLines = input.insert_text.split("\n");
156
+ lines.splice(input.insert_line, 0, ...insertLines);
157
+ await store.write(relativePath, lines.join("\n"));
158
+ return { success: true, message: `The file ${displayPath} has been edited.` };
159
+ }
160
+ case "delete": {
161
+ if (!input.path) {
162
+ throw new Error("delete requires path");
163
+ }
164
+ const relativePath = resolveMemoryPath(input.path);
165
+ const displayPath = memoryDisplayPath(relativePath);
166
+ if (!(await store.exists(relativePath))) {
167
+ return { success: true, message: `Error: The path ${displayPath} does not exist` };
168
+ }
169
+ await store.deletePath(relativePath);
170
+ return { success: true, message: `Successfully deleted ${displayPath}` };
171
+ }
172
+ case "rename": {
173
+ if (!input.old_path || !input.new_path) {
174
+ throw new Error("rename requires old_path and new_path");
175
+ }
176
+ const fromPath = resolveMemoryPath(input.old_path);
177
+ const toPath = resolveMemoryPath(input.new_path);
178
+ const fromDisplay = memoryDisplayPath(fromPath);
179
+ const toDisplay = memoryDisplayPath(toPath);
180
+ if (!(await store.exists(fromPath))) {
181
+ return { success: true, message: `Error: The path ${fromDisplay} does not exist` };
182
+ }
183
+ if (await store.exists(toPath)) {
184
+ return { success: true, message: `Error: The destination ${toDisplay} already exists` };
185
+ }
186
+ await store.rename(fromPath, toPath);
187
+ return { success: true, message: `Successfully renamed ${fromDisplay} to ${toDisplay}` };
188
+ }
189
+ default: {
190
+ const exhaustive = input.command;
191
+ throw new Error(`Unsupported memory command: ${exhaustive}`);
192
+ }
193
+ }
194
+ }
195
+ export const MUTATING_MEMORY_COMMANDS = new Set(["create", "str_replace", "insert", "delete", "rename"]);
196
+ //# sourceMappingURL=memory.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"memory.js","sourceRoot":"","sources":["../../src/memoryfs/memory.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,7 @@
1
+ export declare const MEMORY_ROOT = "/memories";
2
+ export declare const MEMORY_SUBDIR = "memories";
3
+ export declare const FILES_SUBDIR = "files";
4
+ export declare function resolveFsRoot(): string;
5
+ export declare function resolveRelativePath(inputPath: string): string;
6
+ export declare function formatHumanSize(sizeBytes: number): string;
7
+ //# sourceMappingURL=paths.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"paths.d.ts","sourceRoot":"","sources":["../../src/memoryfs/paths.ts"],"names":[],"mappings":"AAGA,eAAO,MAAM,WAAW,cAAc,CAAA;AAEtC,eAAO,MAAM,aAAa,aAAa,CAAA;AACvC,eAAO,MAAM,YAAY,UAAU,CAAA;AAEnC,wBAAgB,aAAa,IAAI,MAAM,CAMtC;AAED,wBAAgB,mBAAmB,CAAC,SAAS,EAAE,MAAM,GAAG,MAAM,CAsB7D;AAED,wBAAgB,eAAe,CAAC,SAAS,EAAE,MAAM,GAAG,MAAM,CAIzD"}
@@ -0,0 +1,39 @@
1
+ import os from "node:os";
2
+ import path from "node:path";
3
+ export const MEMORY_ROOT = "/memories";
4
+ export const MEMORY_SUBDIR = "memories";
5
+ export const FILES_SUBDIR = "files";
6
+ export function resolveFsRoot() {
7
+ const fromEnv = process.env.TERSE_FS_ROOT;
8
+ if (fromEnv && fromEnv.trim().length > 0) {
9
+ return fromEnv.trim();
10
+ }
11
+ return path.join(os.tmpdir(), "terse-memoryfs");
12
+ }
13
+ export function resolveRelativePath(inputPath) {
14
+ const normalized = inputPath.replace(/\\/g, "/").trim();
15
+ if (!normalized) {
16
+ throw new Error("Path is required.");
17
+ }
18
+ const withoutLeadingSlash = normalized.startsWith("/") ? normalized.slice(1) : normalized;
19
+ if (withoutLeadingSlash.includes("\0")) {
20
+ throw new Error("Invalid path.");
21
+ }
22
+ const segments = withoutLeadingSlash.split("/").filter(segment => segment.length > 0);
23
+ if (segments.some(segment => segment === "..")) {
24
+ throw new Error("Path traversal is not allowed.");
25
+ }
26
+ const resolved = path.posix.normalize(segments.join("/") || ".");
27
+ if (resolved === ".." || resolved.startsWith("../")) {
28
+ throw new Error("Path traversal is not allowed.");
29
+ }
30
+ return resolved === "." ? "" : resolved;
31
+ }
32
+ export function formatHumanSize(sizeBytes) {
33
+ if (sizeBytes < 1024)
34
+ return `${sizeBytes}B`;
35
+ if (sizeBytes < 1024 * 1024)
36
+ return `${(sizeBytes / 1024).toFixed(1)}K`;
37
+ return `${(sizeBytes / (1024 * 1024)).toFixed(1)}M`;
38
+ }
39
+ //# sourceMappingURL=paths.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"paths.js","sourceRoot":"","sources":["../../src/memoryfs/paths.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,SAAS,CAAA;AACxB,OAAO,IAAI,MAAM,WAAW,CAAA;AAE5B,MAAM,CAAC,MAAM,WAAW,GAAG,WAAW,CAAA;AAEtC,MAAM,CAAC,MAAM,aAAa,GAAG,UAAU,CAAA;AACvC,MAAM,CAAC,MAAM,YAAY,GAAG,OAAO,CAAA;AAEnC,MAAM,UAAU,aAAa;IACzB,MAAM,OAAO,GAAG,OAAO,CAAC,GAAG,CAAC,aAAa,CAAA;IACzC,IAAI,OAAO,IAAI,OAAO,CAAC,IAAI,EAAE,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QACvC,OAAO,OAAO,CAAC,IAAI,EAAE,CAAA;IACzB,CAAC;IACD,OAAO,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,MAAM,EAAE,EAAE,gBAAgB,CAAC,CAAA;AACnD,CAAC;AAED,MAAM,UAAU,mBAAmB,CAAC,SAAiB;IACjD,MAAM,UAAU,GAAG,SAAS,CAAC,OAAO,CAAC,KAAK,EAAE,GAAG,CAAC,CAAC,IAAI,EAAE,CAAA;IACvD,IAAI,CAAC,UAAU,EAAE,CAAC;QACd,MAAM,IAAI,KAAK,CAAC,mBAAmB,CAAC,CAAA;IACxC,CAAC;IAED,MAAM,mBAAmB,GAAG,UAAU,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,UAAU,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,UAAU,CAAA;IACzF,IAAI,mBAAmB,CAAC,QAAQ,CAAC,IAAI,CAAC,EAAE,CAAC;QACrC,MAAM,IAAI,KAAK,CAAC,eAAe,CAAC,CAAA;IACpC,CAAC;IAED,MAAM,QAAQ,GAAG,mBAAmB,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC,EAAE,CAAC,OAAO,CAAC,MAAM,GAAG,CAAC,CAAC,CAAA;IACrF,IAAI,QAAQ,CAAC,IAAI,CAAC,OAAO,CAAC,EAAE,CAAC,OAAO,KAAK,IAAI,CAAC,EAAE,CAAC;QAC7C,MAAM,IAAI,KAAK,CAAC,gCAAgC,CAAC,CAAA;IACrD,CAAC;IAED,MAAM,QAAQ,GAAG,IAAI,CAAC,KAAK,CAAC,SAAS,CAAC,QAAQ,CAAC,IAAI,CAAC,GAAG,CAAC,IAAI,GAAG,CAAC,CAAA;IAChE,IAAI,QAAQ,KAAK,IAAI,IAAI,QAAQ,CAAC,UAAU,CAAC,KAAK,CAAC,EAAE,CAAC;QAClD,MAAM,IAAI,KAAK,CAAC,gCAAgC,CAAC,CAAA;IACrD,CAAC;IAED,OAAO,QAAQ,KAAK,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,QAAQ,CAAA;AAC3C,CAAC;AAED,MAAM,UAAU,eAAe,CAAC,SAAiB;IAC7C,IAAI,SAAS,GAAG,IAAI;QAAE,OAAO,GAAG,SAAS,GAAG,CAAA;IAC5C,IAAI,SAAS,GAAG,IAAI,GAAG,IAAI;QAAE,OAAO,GAAG,CAAC,SAAS,GAAG,IAAI,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,GAAG,CAAA;IACvE,OAAO,GAAG,CAAC,SAAS,GAAG,CAAC,IAAI,GAAG,IAAI,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,GAAG,CAAA;AACvD,CAAC"}
@@ -0,0 +1,18 @@
1
+ export interface FsEntry {
2
+ path: string;
3
+ isDirectory: boolean;
4
+ sizeBytes: number;
5
+ }
6
+ export declare class LocalFsStore {
7
+ private readonly root;
8
+ constructor(root: string);
9
+ private resolveAbsolute;
10
+ read(relativePath: string): Promise<string>;
11
+ write(relativePath: string, content: string): Promise<void>;
12
+ list(relativePath: string): Promise<FsEntry[]>;
13
+ exists(relativePath: string): Promise<boolean>;
14
+ stat(relativePath: string): Promise<FsEntry>;
15
+ deletePath(relativePath: string): Promise<void>;
16
+ rename(fromPath: string, toPath: string): Promise<void>;
17
+ }
18
+ //# sourceMappingURL=store.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"store.d.ts","sourceRoot":"","sources":["../../src/memoryfs/store.ts"],"names":[],"mappings":"AAMA,MAAM,WAAW,OAAO;IACpB,IAAI,EAAE,MAAM,CAAA;IACZ,WAAW,EAAE,OAAO,CAAA;IACpB,SAAS,EAAE,MAAM,CAAA;CACpB;AAED,qBAAa,YAAY;IACT,OAAO,CAAC,QAAQ,CAAC,IAAI;gBAAJ,IAAI,EAAE,MAAM;IAEzC,OAAO,CAAC,eAAe;IAUjB,IAAI,CAAC,YAAY,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,CAAC;IAI3C,KAAK,CAAC,YAAY,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAM3D,IAAI,CAAC,YAAY,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,EAAE,CAAC;IAgC9C,MAAM,CAAC,YAAY,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAO9C,IAAI,CAAC,YAAY,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC;IAa5C,UAAU,CAAC,YAAY,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAI/C,MAAM,CAAC,QAAQ,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;CAYhE"}