Commit Graph

41 Commits

  • Move skill command handling to AgentSession, update docs
    - Skill commands (/skill:name) now expanded in AgentSession instead of
      interactive mode, enabling them in RPC and print modes
    - Input event can now intercept /skill:name before expansion
    - Updated extensions.md with clearer input event docs and processing order
    - Updated rpc.md: hook -> extension terminology, added skill expansion mentions
    - Added PR attribution to changelog entries for #761
  • feat(coding-agent): add input event for extension input interception (#761)
    * feat(coding-agent): add input event for extension input interception
    
    Extensions can now intercept, transform, or handle user input before the
    agent processes it. Three result types: continue (pass through), transform
    (modify text/images), handled (respond without LLM). Handlers chain
    transforms and short-circuit on handled. Source field identifies origin.
    
    * fix: make source public, use if/else over ternary
    
    * fix: remove response field, extension handles own UI
  • docs: update extension examples READMEs and fix plan-mode references
    - Add missing extensions to examples/extensions/README.md:
      questionnaire.ts, truncated-tool.ts, model-status.ts, rainbow-editor.ts,
      custom-footer.ts, custom-header.ts, overlay-test.ts, shutdown-command.ts,
      interactive-shell.ts, claude-rules.ts, mac-system-theme.ts
    - Update plan-mode.ts -> plan-mode/ (now a directory)
    - Add new System Integration section
    - Update docs/extensions.md plan-mode.ts -> plan-mode/index.ts (17 refs)
    - Add questionnaire.ts to registerTool and ctx.ui.select() examples
    - Expand examples/README.md description
  • coding-agent: example extension to summarize conversation (#684)
    * feat: add summarize extension example
    
    Demonstrates custom UI with markdown rendering and external model
    integration for conversation summarization.
    
    * chore: update examples/extensions/README.md with summarize.ts
  • Change getAllTools() to return ToolInfo[] instead of string[]
    Breaking change: pi.getAllTools() now returns Array<{ name, description }>
    instead of string[]. Extensions needing just names can use .map(t => t.name).
    
    Removes redundant getToolInfo() method added in original PR.
    
    Fixes #647
  • feat(coding-agent): add session naming via /name command and extension API
    - Add SessionInfoEntry type for session metadata
    - Add /name <name> command to set session display name
    - Add pi.setSessionName() and pi.getSessionName() extension API
    - Session selector shows name (in warning color) instead of first message when set
    - Session name included in fuzzy search
    - /session command displays name when set
    
    closes #650
  • Rename /branch command to /fork
    - RPC: branch -> fork, get_branch_messages -> get_fork_messages
    - SDK: branch() -> fork(), getBranchMessages() -> getForkMessages()
    - AgentSession: branch() -> fork(), getUserMessagesForBranching() -> getUserMessagesForForking()
    - Extension events: session_before_branch -> session_before_fork, session_branch -> session_fork
    - Settings: doubleEscapeAction 'branch' -> 'fork'
    
    fixes #641
  • feat(coding-agent): add model_select extension hook
    Fires when the model changes via /model command, model cycling (Ctrl+P),
    or session restore. Includes source field and previousModel.
    
    Add model-status.ts example extension demonstrating status bar updates.
    
    closes #628
  • docs(coding-agent): document model_select hook
    Add CHANGELOG entry and extension documentation for the new model_select
    event that fires on model changes via /model, Ctrl+P, or session restore.
  • feat: add ctx.ui.setWorkingMessage() extension API
    Allows extensions to customize the streaming loader message.
    Pass undefined to restore default.
  • fix(coding-agent): remove -- from registerFlag calls
    This was causing the agent sometimes to pick up on the incorrect syntax when
    asked to write extensions with flags
  • feat(coding-agent): add interactive-shell.ts extension example
    Demonstrates running interactive commands (vim, git rebase, htop, etc.)
    with full terminal access using user_bash event and ctx.ui.custom().
    
    - Auto-detects interactive commands from built-in list
    - !i prefix to force interactive mode
    - Configurable via INTERACTIVE_COMMANDS/INTERACTIVE_EXCLUDE env vars
    
    closes #532
  • feat(coding-agent): add user_bash event and theme API extensions
    - user_bash event for intercepting ! and !! commands (#528)
    - Extensions can return { operations } or { result } to redirect/replace
    - executeBashWithOperations() for custom BashOperations execution
    - session.recordBashResult() for extensions handling bash themselves
    - Theme API: getAllThemes(), getTheme(), setTheme() on ctx.ui
    - mac-system-theme.ts example: sync with macOS dark/light mode
    - Updated ssh.ts to use user_bash event
  • Allow extensions to modify system prompt in before_agent_start
    - Add systemPrompt to BeforeAgentStartEvent so extensions can see current prompt
    - Change systemPromptAppend to systemPrompt in BeforeAgentStartEventResult for full replacement
    - Extensions can now chain modifications (each sees the result of previous)
    - Update ssh.ts to replace local cwd with remote cwd in system prompt
    - Update pirate.ts, claude-rules.ts, preset.ts to use new API
    
    fixes #575
  • feat(coding-agent): add pluggable operations for remote tool execution
    Adds optional operations parameter to create*Tool functions enabling
    delegation to remote systems (SSH, containers, etc.):
    
    - ReadOperations: readFile, access, detectImageMimeType
    - WriteOperations: writeFile, mkdir
    - EditOperations: readFile, writeFile, access
    - BashOperations: exec (with streaming, signal, timeout)
    
    Add ssh.ts example demonstrating --ssh flag for remote execution.
    Built-in renderers used automatically for overrides without custom renderers.
    
    fixes #564
  • feat(coding-agent): use built-in renderers for tool overrides without custom renderers
    When overriding a built-in tool (read, bash, edit, write, grep, find, ls)
    without providing renderCall/renderResult, the built-in renderer is now
    used automatically. This allows wrapping built-in tools for logging or
    access control without reimplementing the UI (syntax highlighting, diffs, etc.).
  • feat(coding-agent): add tool override support via extensions
    - Add setActiveTools() to ExtensionAPI for dynamic tool management
    - Extensions can now override, wrap, or disable built-in tools
    - Add tool-override.ts example demonstrating the pattern
    - Update documentation for tool override capabilities
  • refactor(coding-agent): simplify extension runtime architecture
    - Replace per-extension closures with shared ExtensionRuntime
    - Split context actions: ExtensionContextActions (required) + ExtensionCommandContextActions (optional)
    - Rename LoadedExtension to Extension, remove setter methods
    - Change runner.initialize() from options object to positional params
    - Derive hasUI from uiContext presence (no separate param)
    - Add warning when extensions override built-in tools
    - RPC and print modes now provide full command context actions
    
    BREAKING CHANGE: Extension system types and initialization API changed.
    See CHANGELOG.md for migration details.
  • feat(coding-agent): add ctx.ui.setEditorComponent() extension API
    - Add setEditorComponent() to ctx.ui for custom editor components
    - Add CustomEditor base class for extensions (handles app keybindings)
    - Add keybindings parameter to ctx.ui.custom() factory (breaking change)
    - Add modal-editor.ts example (vim-like modes)
    - Add rainbow-editor.ts example (animated text highlighting)
    - Update docs: extensions.md, tui.md Pattern 7
    - Clean up terminal on TUI render errors
  • feat(coding-agent): add timeout option to extension dialogs with live countdown
    Extension UI dialogs (select, confirm, input) now support a timeout option
    that auto-dismisses with a live countdown display. Simpler alternative to
    manually managing AbortSignal for timed dialogs.
    
    Also adds ExtensionUIDialogOptions type export and updates RPC mode to
    forward timeout to clients.
  • Add ExtensionAPI methods, preset example, and TUI documentation improvements
    - ExtensionAPI: setModel(), getThinkingLevel(), setThinkingLevel() methods
    - New preset.ts example with plan/implement presets for model/thinking/tools switching
    - Export all UI components from pi-coding-agent for extension use
    - docs/tui.md: Common Patterns section with copy-paste code for SelectList, BorderedLoader, SettingsList, setStatus, setWidget, setFooter
    - docs/tui.md: Key Rules section for extension UI development
    - docs/extensions.md: Exhaustive example links for all ExtensionAPI methods and events
    - System prompt now references docs/tui.md for TUI development
    
    Fixes #509, relates to #347
  • Export truncation utilities for custom tools, add truncated-tool example
    - Export truncateHead, truncateTail, truncateLine, formatSize, DEFAULT_MAX_BYTES, DEFAULT_MAX_LINES from package
    - Add examples/extensions/truncated-tool.ts showing proper output truncation with custom rendering
    - Document output truncation best practices in docs/extensions.md
  • Extensions: add pi.sendUserMessage() for sending user messages
    Adds sendUserMessage() to the extension API, allowing extensions to send
    actual user messages (role: user) rather than custom messages. Unlike
    sendMessage(), this always triggers a turn and behaves as if the user
    typed the message.
    
    - Add SendUserMessageHandler type and sendUserMessage() to ExtensionAPI
    - Wire handler through loader, runner, and all modes
    - Implement via prompt() with expandPromptTemplates: false
    - Add send-user-message.ts example with /ask, /steer, /followup commands
    - Document in extensions.md
    
    fixes #483
  • Add ctx.ui.setFooter() for extensions to replace footer component
    Extensions can now replace the built-in footer with a custom component:
    - setFooter(factory) replaces with custom component
    - setFooter(undefined) restores built-in footer
    
    Includes example extension demonstrating context usage display.
    
    Closes #481
  • Add customTools option back to createAgentSession SDK
    - Accepts ToolDefinition[] directly (simplified from old { path?, tool } format)
    - Tools are combined with extension-registered tools
    - Updated sdk.md documentation
    - Updated CHANGELOG
  • Add Custom UI section, update CHANGELOG migration docs
    - Add ## Custom UI section consolidating dialogs, widgets, custom components, message rendering, theme colors
    - Simplify ctx.ui and pi.registerMessageRenderer in other sections to reference Custom UI
    - Update CHANGELOG to reflect auto-migration of commands/ to prompts/
  • Restructure extensions.md: add Custom Tools section, improve sendMessage docs
    - Add ## Custom Tools section with Tool Definition, Multiple Tools, Custom Rendering
    - Expand pi.sendMessage docs with deliverAs mode explanations
    - Add Extension Styles subsection (single file, dir, package.json)
    - Expand ExtensionCommandContext with waitForIdle, newSession, branch, navigateTree
    - Replace lodash with zod in examples
    - Various fixes and reorganization
  • Add migration for commands->prompts, warn about deprecated hooks/tools dirs
    - Auto-migrate commands/ to prompts/ on startup
    - Warn if hooks/ or tools/ directories contain custom extensions
    - Show deprecation warnings in interactive mode with keypress to continue
    - Update CHANGELOG and docs with full migration guide
  • Merge hooks and custom-tools into unified extensions system (#454)
    Breaking changes:
    - Settings: 'hooks' and 'customTools' arrays replaced with 'extensions'
    - CLI: '--hook' and '--tool' flags replaced with '--extension' / '-e'
    - API: HookMessage renamed to CustomMessage, role 'hookMessage' to 'custom'
    - API: FileSlashCommand renamed to PromptTemplate
    - API: discoverSlashCommands() renamed to discoverPromptTemplates()
    - Directories: commands/ renamed to prompts/ for prompt templates
    
    Migration:
    - Session version bumped to 3 (auto-migrates v2 sessions)
    - Old 'hookMessage' role entries converted to 'custom'
    
    Structural changes:
    - src/core/hooks/ and src/core/custom-tools/ merged into src/core/extensions/
    - src/core/slash-commands.ts renamed to src/core/prompt-templates.ts
    - examples/hooks/ and examples/custom-tools/ merged into examples/extensions/
    - docs/hooks.md and docs/custom-tools.md merged into docs/extensions.md
    
    New test coverage:
    - test/extensions-runner.test.ts (10 tests)
    - test/extensions-discovery.test.ts (26 tests)
    - test/prompt-templates.test.ts