agent-sh 0.7.0 → 0.9.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.
Files changed (86) hide show
  1. package/README.md +28 -33
  2. package/dist/agent/agent-loop.d.ts +31 -8
  3. package/dist/agent/agent-loop.js +277 -66
  4. package/dist/agent/conversation-state.d.ts +41 -9
  5. package/dist/agent/conversation-state.js +340 -17
  6. package/dist/agent/history-file.d.ts +36 -0
  7. package/dist/agent/history-file.js +167 -0
  8. package/dist/agent/nuclear-form.d.ts +41 -0
  9. package/dist/agent/nuclear-form.js +176 -0
  10. package/dist/agent/system-prompt.d.ts +4 -5
  11. package/dist/agent/system-prompt.js +16 -11
  12. package/dist/agent/token-budget.d.ts +13 -0
  13. package/dist/agent/token-budget.js +50 -0
  14. package/dist/agent/tool-protocol.d.ts +83 -0
  15. package/dist/agent/tool-protocol.js +386 -0
  16. package/dist/agent/tools/user-shell.js +4 -1
  17. package/dist/agent/types.d.ts +21 -1
  18. package/dist/context-manager.d.ts +0 -1
  19. package/dist/context-manager.js +5 -110
  20. package/dist/core.d.ts +7 -7
  21. package/dist/core.js +76 -180
  22. package/dist/event-bus.d.ts +40 -0
  23. package/dist/event-bus.js +20 -1
  24. package/dist/extension-loader.d.ts +5 -0
  25. package/dist/extension-loader.js +104 -17
  26. package/dist/extensions/agent-backend.d.ts +13 -0
  27. package/dist/extensions/agent-backend.js +167 -0
  28. package/dist/extensions/command-suggest.d.ts +3 -3
  29. package/dist/extensions/command-suggest.js +4 -3
  30. package/dist/extensions/index.d.ts +19 -0
  31. package/dist/extensions/index.js +25 -0
  32. package/dist/extensions/slash-commands.d.ts +1 -1
  33. package/dist/extensions/slash-commands.js +44 -1
  34. package/dist/extensions/terminal-buffer.d.ts +1 -1
  35. package/dist/extensions/terminal-buffer.js +22 -8
  36. package/dist/extensions/tui-renderer.js +177 -122
  37. package/dist/index.js +14 -20
  38. package/dist/settings.d.ts +25 -2
  39. package/dist/settings.js +25 -4
  40. package/dist/{input-handler.d.ts → shell/input-handler.d.ts} +1 -1
  41. package/dist/{input-handler.js → shell/input-handler.js} +60 -43
  42. package/dist/{output-parser.d.ts → shell/output-parser.d.ts} +1 -1
  43. package/dist/{output-parser.js → shell/output-parser.js} +1 -1
  44. package/dist/{shell.d.ts → shell/shell.d.ts} +8 -2
  45. package/dist/{shell.js → shell/shell.js} +24 -6
  46. package/dist/types.d.ts +49 -32
  47. package/dist/utils/ansi.d.ts +10 -0
  48. package/dist/utils/ansi.js +27 -0
  49. package/dist/utils/compositor.d.ts +62 -0
  50. package/dist/utils/compositor.js +88 -0
  51. package/dist/utils/diff-renderer.js +92 -4
  52. package/dist/utils/floating-panel.d.ts +34 -3
  53. package/dist/utils/floating-panel.js +315 -82
  54. package/dist/utils/handler-registry.d.ts +26 -10
  55. package/dist/utils/handler-registry.js +52 -16
  56. package/dist/utils/line-editor.d.ts +32 -3
  57. package/dist/utils/line-editor.js +218 -36
  58. package/dist/utils/markdown.d.ts +1 -0
  59. package/dist/utils/markdown.js +4 -4
  60. package/dist/utils/message-utils.d.ts +35 -0
  61. package/dist/utils/message-utils.js +75 -0
  62. package/dist/utils/terminal-buffer.d.ts +9 -1
  63. package/dist/utils/terminal-buffer.js +31 -2
  64. package/dist/utils/tool-display.d.ts +1 -0
  65. package/dist/utils/tool-display.js +1 -1
  66. package/dist/utils/tool-interactive.d.ts +12 -0
  67. package/dist/utils/tool-interactive.js +53 -0
  68. package/examples/extensions/ash-acp-bridge/README.md +39 -0
  69. package/examples/extensions/ash-acp-bridge/package.json +23 -0
  70. package/examples/extensions/ash-acp-bridge/src/index.ts +571 -0
  71. package/examples/extensions/ash-acp-bridge/tsconfig.json +14 -0
  72. package/examples/extensions/ash-mcp-bridge/README.md +72 -0
  73. package/examples/extensions/ash-mcp-bridge/index.ts +154 -0
  74. package/examples/extensions/ash-mcp-bridge/package.json +9 -0
  75. package/examples/extensions/claude-code-bridge/index.ts +77 -1
  76. package/examples/extensions/interactive-prompts.ts +82 -110
  77. package/examples/extensions/overlay-agent.ts +84 -38
  78. package/examples/extensions/peer-mesh.ts +450 -0
  79. package/examples/extensions/pi-bridge/index.ts +87 -2
  80. package/examples/extensions/questionnaire.ts +249 -0
  81. package/examples/extensions/tmux-pane.ts +307 -0
  82. package/examples/extensions/web-access.ts +327 -0
  83. package/package.json +9 -1
  84. package/dist/extensions/overlay-agent.d.ts +0 -11
  85. package/dist/extensions/overlay-agent.js +0 -43
  86. package/examples/extensions/terminal-buffer.ts +0 -184
package/README.md CHANGED
@@ -1,36 +1,22 @@
1
1
  # agent-sh
2
2
 
3
+ An agent that lives in a shell — not a shell that lives in an agent.
4
+
3
5
  [![npm version](https://img.shields.io/npm/v/agent-sh.svg)](https://www.npmjs.com/package/agent-sh)
4
6
  [![license](https://img.shields.io/npm/l/agent-sh.svg)](https://github.com/guanyilun/agent-sh/blob/main/LICENSE)
5
7
 
6
- Not a shell that lives in an agent an agent that lives in a shell.
7
-
8
- I live in a terminal. I don't want an agent that can run shell commands when it needs to — I want my shell, with an agent I can reach for when *I* need to. Most AI tools get this backwards: the LLM drives the experience and the shell is bolted on as an afterthought. No real PTY, no job control, no vim, fragile `cd` tracking. The agent is the main character and your terminal is a prop.
8
+ Most AI terminal tools get this backwards: the LLM drives the experience and the shell is bolted on as an afterthought. No real PTY, no job control, no vim, fragile `cd` tracking. The agent is the main character and your terminal is a prop.
9
9
 
10
10
  agent-sh flips this. It's your shell first — full PTY, your rc config, your aliases, everything just works. But type `>` at the start of a line, and you're talking to an agent that has full context of what you've been doing.
11
11
 
12
12
  ```
13
- src $ ls -la # real shell command
14
- src $ cd ../tests && npm test # real cd, env, aliases — all just work
15
- src $ vim file.ts # opens vim in the same PTY
16
- src $ > explain the last error # agent investigates using its own tools
17
- src $ > deploy to staging # agent runs it in your live shell
13
+ ~ $ ls -la # real shell command
14
+ ~ $ cd ../tests && npm test # real cd, env, aliases — all just work
15
+ ~ $ vim file.ts # opens vim in the same PTY
16
+ ~ $ > explain the last error # agent investigates using its own tools
17
+ ~ $ > deploy to staging # agent runs it in your live shell
18
18
  ```
19
19
 
20
- ## Key Features
21
-
22
- **Real terminal, zero compromise.** Full PTY with your shell config, aliases, and environment. Shell starts instantly — the agent connects asynchronously in the background.
23
-
24
- **Context-aware agent.** Every query includes your cwd, recent commands, and their output. Run a failing test, type `> fix this`, and the agent knows exactly what happened. It has built-in tools for file read/write/edit, bash, grep, glob — no external setup needed.
25
-
26
- **Agent decides how to help.** One entry point (`>`), three tool categories. The agent uses scratchpad tools to investigate, `display` to show you output, and `user_shell` for commands with lasting effects. No need to pick a mode — the agent reasons about which tools to use based on your intent.
27
-
28
- **Any LLM, any backend.** Works with any OpenAI-compatible API out of the box. Define multiple providers in settings and cycle between models at runtime with Shift+Tab. Or swap in a completely different agent — [Claude Code](examples/extensions/claude-code-bridge/) and [pi](examples/extensions/pi-bridge/) run as drop-in backend extensions.
29
-
30
- **Extensible by design.** The entire system is built on a typed event bus. Extensions can add custom input modes, content transforms (render LaTeX as images, Mermaid as diagrams), themes, slash commands, or replace the agent backend entirely. The built-in TUI renderer is itself just an extension — nothing is special.
31
-
32
- **Embeddable as a library.** The core is a headless kernel — `import { createCore } from "agent-sh"` to build WebSocket servers, REST APIs, Electron apps, or test harnesses. No terminal required.
33
-
34
20
  ## Quick Start
35
21
 
36
22
  ```bash
@@ -42,34 +28,43 @@ Set `OPENAI_API_KEY` in your environment (or configure providers in `~/.agent-sh
42
28
 
43
29
  Requires Node.js 18+.
44
30
 
45
- ## Agent Mode
31
+ ## Key Features
46
32
 
47
- Type `>` at the start of a line to talk to the agent. The agent decides how to help:
33
+ **Real terminal, zero compromise.** Full PTY with your shell config, aliases, and environment. Shell starts instantly — the agent connects asynchronously in the background.
48
34
 
49
- - **Scratchpad tools** (`bash`, `read_file`, `grep`, `glob`, etc.) for investigation. Output goes to the agent, not your terminal.
50
- - **`display`** — shows output in your terminal (e.g. `cat`, `git log`). You see it; the agent doesn't process it.
51
- - **`user_shell`** — runs commands with lasting effects (`cd`, `npm install`, etc.) in your live shell.
35
+ **One entry point, three tool categories.** Type `>` and agent-sh figures out how to help. Scratchpad tools (`bash`, `read_file`, `grep`, `glob`) for investigation. `display` to show you output. `user_shell` for commands with lasting effects in your live shell. No modes to pick — the agent reasons about which tools to use based on your intent.
52
36
 
53
- Everything else works as a normal shell commands go straight to the PTY. Input modes are extensiblesee [Extensions: Custom Input Modes](docs/extensions.md#custom-input-modes).
37
+ **Context that just works.** Every query includes your cwd, recent commands, and their output. Run a failing test, type `> fix this`, and agent-sh knows exactly what happened. Context management works like shell history continuous, persistent across restarts, no sessions to manage. See [Context Management](docs/context-management.md).
38
+
39
+ **Any LLM, any backend.** agent-sh works with any OpenAI-compatible API out of the box. Define multiple providers in settings and cycle between models at runtime with Shift+Tab. Or swap in a completely different agent — [Claude Code](examples/extensions/claude-code-bridge/) and [pi](examples/extensions/pi-bridge/) run as drop-in backend extensions.
40
+
41
+ **Extensible by design.** The entire system is built on a typed event bus. Extensions can add custom input modes, content transforms (render LaTeX as images, Mermaid as diagrams), themes, slash commands, or replace the agent backend entirely. The built-in TUI renderer is itself just an extension.
42
+
43
+ **Embeddable as a library.** The core is a headless kernel — `import { createCore } from "agent-sh"` to build WebSocket servers, REST APIs, Electron apps, or test harnesses. No terminal required.
54
44
 
55
- ### Slash Commands
45
+ ## Slash Commands
56
46
 
57
47
  | Command | Description |
58
48
  |---|---|
59
49
  | `/help` | Show available commands |
60
50
  | `/model [name]` | Cycle to the next model, or switch to a specific one |
61
51
  | `/backend [name]` | List backends, or switch to a named backend |
52
+ | `/compact` | Compact conversation (free up context space) |
53
+ | `/context` | Show context budget usage |
54
+ | `/thinking [level]` | Set reasoning effort (off, low, medium, high) |
62
55
 
63
56
  ## Configuration
64
57
 
65
- Configure via `~/.agent-sh/settings.json`. See the [Usage Guide](docs/usage.md#configuration) for the full settings reference (providers, models, extensions, skills, and more).
58
+ Configure via `~/.agent-sh/settings.json`. See the [Usage Guide](docs/usage.md#configuration) for the full settings reference.
66
59
 
67
60
  ## Documentation
68
61
 
69
- - [Usage Guide](docs/usage.md) — providers, models, configuration, provider profiles
70
- - [Internal Agent](docs/agent.md) — how the agent loop works: tools, context, streaming
71
- - [Architecture](docs/architecture.md) — design philosophy, component overview, project structure
62
+ - [Usage Guide](docs/usage.md) — providers, models, configuration
63
+ - [Internal Agent](docs/agent.md) — tools, context, streaming
64
+ - [Context Management](docs/context-management.md) — three-tier history, token budget
65
+ - [Architecture](docs/architecture.md) — design philosophy, component overview
72
66
  - [Extensions](docs/extensions.md) — event bus, content transforms, custom backends, theming
67
+ - [TUI Composition](docs/tui-composition.md) — compositor, render surfaces, stream routing
73
68
  - [Library Usage](docs/library.md) — embedding agent-sh in your own apps
74
69
  - [Troubleshooting](docs/troubleshooting.md) — common errors and debug mode
75
70
 
@@ -16,32 +16,57 @@ import type { EventBus } from "../event-bus.js";
16
16
  import type { AgentMode } from "../types.js";
17
17
  import type { ContextManager } from "../context-manager.js";
18
18
  import type { LlmClient } from "../utils/llm-client.js";
19
- import type { HandlerRegistry } from "../utils/handler-registry.js";
19
+ import type { HandlerFunctions } from "../utils/handler-registry.js";
20
20
  import type { AgentBackend, ToolDefinition } from "./types.js";
21
+ import type { Compositor } from "../utils/compositor.js";
22
+ export interface AgentLoopConfig {
23
+ bus: EventBus;
24
+ contextManager: ContextManager;
25
+ llmClient: LlmClient;
26
+ handlers: HandlerFunctions;
27
+ modes?: AgentMode[];
28
+ initialModeIndex?: number;
29
+ compositor?: Compositor;
30
+ }
21
31
  export declare class AgentLoop implements AgentBackend {
22
- private bus;
23
- private contextManager;
24
- private llmClient;
25
- private handlers;
26
32
  private abortController;
27
33
  private toolRegistry;
34
+ private historyFile;
28
35
  private conversation;
29
36
  private fileReadCache;
37
+ private tokenBudget;
30
38
  private modes;
31
39
  private currentModeIndex;
32
40
  private boundListeners;
41
+ private ctorListeners;
42
+ private ctorPipeListeners;
33
43
  private lastProjectSkillNames;
34
44
  private static readonly THINKING_LEVELS;
45
+ private bus;
46
+ private contextManager;
47
+ private llmClient;
48
+ private handlers;
35
49
  private thinkingLevel;
36
- constructor(bus: EventBus, contextManager: ContextManager, llmClient: LlmClient, handlers: HandlerRegistry, modeConfig?: AgentMode[], initialModeIndex?: number);
50
+ private compositor;
51
+ private toolProtocol;
52
+ constructor(config: AgentLoopConfig);
37
53
  /** Subscribe to bus events — activates this backend. */
38
54
  wire(): void;
39
55
  /** Unsubscribe from bus events — deactivates this backend. */
40
56
  unwire(): void;
41
57
  /** Register a tool (used by extensions via ctx.registerTool). */
42
58
  registerTool(tool: ToolDefinition): void;
59
+ /** Unregister a tool by name. */
60
+ unregisterTool(name: string): void;
43
61
  /** Get all registered tools. */
44
62
  getTools(): ToolDefinition[];
63
+ private instructions;
64
+ /** Register a named instruction block for the system prompt. */
65
+ registerInstruction(name: string, text: string): void;
66
+ /** Remove a named instruction block. */
67
+ removeInstruction(name: string): void;
68
+ /** Get instruction blocks registered by extensions. */
69
+ getInstructionSections(): string[];
45
70
  kill(): void;
46
71
  private cancel;
47
72
  /** Check if reasoning_effort should be sent for the current model/provider. */
@@ -63,8 +88,6 @@ export declare class AgentLoop implements AgentBackend {
63
88
  */
64
89
  private registerHandlers;
65
90
  private handleQuery;
66
- /** Max tokens before auto-compaction (conservative default). */
67
- private maxContextTokens;
68
91
  /**
69
92
  * Core agent loop: stream LLM response → execute tools → repeat.
70
93
  * Returns the final accumulated response text.