Skip to content

v1.36.1

Latest

Choose a tag to compare

@github-actions github-actions released this 23 Mar 13:53

A full, first-class OpenRouter provider has been added, allowing users to route requests across OpenAI, Anthropic, Google, and other backends through a single API key and endpoint.

  • New provider package — pkg/model/provider/openrouter/ (adapter.go, client.go, client_test.go): Implements the chat-completion streaming client, SSE stream adapter, message conversion, reasoning/thinking-budget mapping, and embedding support. Uses the github.com/revrost/go-openrouter Go module.
  • Provider registration — pkg/model/provider/provider.go: openrouter added to CoreProviders list and to createDirectProvider / applyModelDefaults switch trees.
  • Thinking-only model detection — isOpenRouterThinkingOnlyModel() strips the provider prefix (e.g. openai/o3-mini) before delegating to the existing OpenAI thinking-model check. Default ThinkingBudget{Effort: "high"} is applied.
  • Auto-detection — pkg/config/auto.go: OPENROUTER_API_KEY registered in cloudProviders and DefaultModels (openai/gpt-5-mini). Provider precedence: anthropic > openai > google > mistral > openrouter > dmr.
  • Tests — pkg/config/auto_test.go, pkg/model/provider/provider_test.go, pkg/model/provider/model_defaults_test.go: Coverage for provider detection, precedence, catalog membership, default model, and thinking-model defaults.
  • Documentation:
    • New docs page: docs/providers/openrouter/index.md — setup, inline/named model config, provider options table, thinking budget, embeddings, auto-detection callout.
    • Updated: docs/providers/overview/index.md (card + comparison table), docs/concepts/models/index.md (provider table row), docs/configuration/overview/index.md (env var table), docs/getting-started/installation/index.md (API key example).
    • README.md: OpenRouter mentioned in provider list and API key export example.
  • Example config — examples/openrouter.yaml: Demonstrates chat model with web-search plugin, thinking budget, and an embedding model reference.
  • Dependency — go.mod / go.sum: Added github.com/revrost/go-openrouter v1.1.7 and indirect dep github.com/mattn/go-sqlite3 v1.14.37.

The previously flat max_old_tool_call_tokens / num_history_items fields have been replaced by a structured compaction configuration block that supports four strategies: summary, custom (script), rolling, and agent.

  • pkg/config/latest/types.go: New types — CompactionConfig, CompactionThreshold (with ThresholdKind enum: percentage / tokens / messages), and full JSON + YAML marshal/unmarshal support. Old MaxOldToolCallTokens and NumHistoryItems fields on AgentConfig replaced by Compaction *CompactionConfig. New AddPromptScripts []string field also added (see feature docker#5).

  • agent-schema.json: Schema block for compaction object with type, threshold (oneOf integer/string), max_old_tool_call_tokens, script, model, agent. Removed old top-level max_old_tool_call_tokens and num_history_items.

  • pkg/config/latest/validate.go: validateCompaction() added — validates type enum, threshold, script/agent/model field applicability per type.

  • CHANGELOG.md: Setting path updated from max_old_tool_call_tokens to compaction.max_old_tool_call_tokens.

  • pkg/agent/agent.go: maxOldToolCallTokens and numHistoryItems replaced by compaction *latest.CompactionConfig. AddPromptScripts() accessor added.

  • pkg/agent/opts.go: WithCompaction(*latest.CompactionConfig) replaces WithNumHistoryItems(). WithMaxOldToolCallTokens now writes into the compaction struct. WithAddPromptScripts() added.

  • pkg/compaction/compaction.go: New ShouldCompactWithThreshold() that accepts an absolute token threshold (skipping percentage math when positive). ShouldCompact() is now a thin wrapper.

  • pkg/compaction/compaction_test.go: TestShouldCompactWithThreshold — absolute threshold, exact boundary, zero-context-limit override, zero-threshold fallback.

  • pkg/runtime/session_compaction.go: Major expansion:

    • compactionOutcome struct — unifies result type across strategies.
    • runCompaction() dispatches to the chosen strategy.
    • runCompactionScript() — executes an external script with JSON stdin/stdout, 30 s timeout, falls back to summary on failure.
    • runRollingCompaction() — keeps only the N most recent conversation messages.
    • runAgentCompaction() — delegates to another named agent via the team.
    • normalizeCompactionMessages() — validates roles and tool-call/result pairing in script output.
    • doCompact() updated to use the new engine and emit SessionSummaryWithMessages events when structured messages are produced.
  • pkg/session/session.go:

    • New CompactionMessages []chat.Message field on Item; IsCompaction() predicate; NewCompactionItem() constructor; deepCopyChatMessages() helper.
    • buildSessionSummaryMessages() renamed to buildCompactionMessages() — handles both legacy summaries and structured compaction items.
    • GetMessages() applies rolling message trimming from CompactionConfig.Threshold.Messages() instead of NumHistoryItems.
    • BuildFullSystemPrompt() — new exported helper that concatenates all (invariant + context-specific) system messages for display/export.
  • pkg/session/store.go: Store interface gains AddCompactionMessages(). InMemorySessionStore and SQLiteSessionStore implement it. SQLite implementation includes syncMessagesColumn() for schema migration.

  • pkg/session/branch.go: cloneSessionItem() handles compaction items.

  • pkg/session/session_test.go: TestGetMessages_CompactionMessagesReplaceOlderHistory — validates that compaction items replace older history while preserving newer items.

  • pkg/session/branch_test.go: Clone test for compaction items.

  • pkg/runtime/loop.go: ShouldCompact → ShouldCompactWithThreshold with the agent's effective threshold. compactIfNeeded likewise updated.

  • pkg/runtime/persistent_runtime.go: handleEvent persists CompactionMessages via the new store method. New Summarize() wrapper ensures direct compaction requests are also persisted.

  • pkg/runtime/runtime_test.go: TestSummarize_CompactionScriptSuccess and TestSummarize_CompactionScriptFallbacksToBuiltin — end-to-end tests for custom script compaction including fallback behavior.

  • pkg/runtime/event.go: SessionSummaryEvent gains CompactionMessages []chat.Message. New SessionSummaryWithMessages() constructor.

  • docs/configuration/agents/index.md: Full "Session Compaction" section with property table and YAML examples for all four strategies. Old num_history_items references removed.

  • docs/community/troubleshooting/index.md: Troubleshooting references updated from num_history_items to compaction.

  • Examples: examples/compaction_agent.yaml, examples/compaction_rolling.yaml, examples/compaction_script.yaml, examples/compaction_summary.yaml, examples/compaction_script.py (full Python reference implementation).

  • examples/README.md: Table updated with new compaction examples.

  • pkg/model/provider/gemini/embed.go: Implements CreateEmbedding() and CreateBatchEmbedding() on the Gemini client using genai.EmbedContent with RETRIEVAL_DOCUMENT task type. This enables RAG embedding strategies to use Gemini models.

  • pkg/model/provider/oaistream/schema.go (new): Extracts ConvertParametersToSchema, walkSchema, makeAllRequired, removeFormatFields, and fixSchemaArrayItems into a shared package. These were previously duplicated in the OpenAI provider.

  • pkg/model/provider/openai/schema.go: Now delegates to oaistream.ConvertParametersToSchema(). Local implementations kept for backward compatibility but the canonical logic is in oaistream.

  • The OpenRouter provider also uses oaistream.ConvertParametersToSchema for tool schemas.

A new config field lets agents run external commands at startup and append their stdout to the system prompt.

  • agent-schema.json: add_prompt_scripts array field added.
  • pkg/config/latest/types.go: AddPromptScripts []string on AgentConfig.
  • pkg/agent/agent.go / opts.go: addPromptScripts field + WithAddPromptScripts() option.
  • pkg/session/prompt_script.go (new): runPromptScript() — splits the command string, runs it with a 30 s timeout in the agent's working directory, returns trimmed stdout.
  • pkg/session/session.go: buildContextSpecificSystemMessages() iterates a.AddPromptScripts() and appends each script's output as a system message.
  • docs/configuration/agents/index.md: Row added to the agent properties table.
  • examples/prompt_scripts.yaml: Example config.

A new --export root-level flag auto-exports the session as HTML after each conversation turn, in both TUI and exec/CLI modes.

  • cmd/root/root.go: --export persistent flag registered (NoOptDefVal = "true" for boolean-style use).
  • cmd/root/run.go: runExecFlags.exportPath populated from the flag; buildAppOpts wires app.WithAutoExport(filename).
  • pkg/app/app.go: autoExportEnabled, autoExportPath, systemPrompt fields; WithAutoExport() option; RunAutoExport(), AutoExportEnabled(), SetSystemPrompt(), SystemPrompt() methods.
  • pkg/cli/runner.go: Config.ExportPath field; autoExport() closure called after each conversation turn in all input modes (piped, multi-message, interactive). Captures AgentInfoEvent.Instruction for the system prompt.
  • pkg/tui/page/chat/runtime_events.go: handleStreamStopped fires RunAutoExport as a background Bubble Tea command.

The assembled system prompt is now included in HTML exports as a collapsible section.

  • pkg/app/export/html.go: SessionData.SystemPrompt field; SessionToFile() signature gains instruction parameter; Generate() renders markdown to HTML and passes it as SystemPromptHTML.
  • pkg/app/export/export.html: Collapsible "System Prompt" section with chevron toggle.
  • pkg/app/export/export.js: Auto-scroll to bottom on load and content mutation (for live-reload). toggle() function for collapsible sections.

The system prompt is now visible as a collapsible message block in the TUI chat view.

  • pkg/tui/types/types.go: MessageTypeSystemPrompt constant; SystemPrompt() constructor.

  • pkg/tui/styles/styles.go / theme.go: SystemPromptStyle (normal border, muted foreground) and SystemPromptHeaderStyle (bold, muted text).

  • pkg/tui/components/message/message.go: expanded field for collapsible state; renderSystemPrompt() with collapsed preview (3 lines) and expanded markdown rendering; Toggle() and IsToggleLine() methods.

  • pkg/tui/components/messages/messages.go: AddSystemPromptMessage() method (idempotent — only adds once). Mouse-click handler dispatches to toggleable interface for expand/collapse. AddWelcomeMessage() now ignores system-prompt messages when deciding whether to show the welcome.

  • pkg/tui/page/chat/runtime_events.go: AgentInfoEvent handler calls SetSystemPrompt() on the app and AddSystemPromptMessage() on the messages view.

  • pkg/runtime/event.go: AgentInfoEvent.Instruction field; AgentInfo() constructor updated.

  • pkg/runtime/runtime.go: CurrentAgentInfo struct gains Instruction. EmitStartupInfo() calls session.BuildFullSystemPrompt(a, sess) to build the full prompt.

  • pkg/runtime/loop.go: All AgentInfo() call sites updated to pass a.Instruction().

  • pkg/runtime/runtime_test.go: All expected AgentInfo events updated with the instruction string.

  • pkg/runtime/loop.go: New hadToolCalls flag tracks whether the previous turn made tool calls. If the model stops without content right after tool calls (res.Stopped && len(res.Calls) == 0 && hadToolCalls && res.Content == ""), a user-role nudge message ("Reply to the provided tool response.") is injected and the loop continues for one more turn. This prevents silent stops after tool execution.

Custom provider configurations are now propagated into RAG strategy builders so that RAG embedding and chat models can use custom providers.

  • pkg/rag/builder.go: ManagersBuildConfig.Providers field; passed to BuildContext and to reranking provider creation via options.WithProviders.

  • pkg/rag/strategy/strategy.go: BuildContext.Providers field.

  • pkg/rag/strategy/embedding.go: Embedding provider creation now passes options.WithProviders.

  • pkg/rag/strategy/semantic_embeddings.go: Chat provider creation likewise uses options.WithProviders.

  • cmd/root/rag.go (new): docker-agent rag <agent-file> <rag-name> <query> — loads a config, initializes a named RAG source, runs a query, and prints results as JSON. Useful for testing RAG sources outside a full agent session.

  • cmd/root/root.go: newRAGCmd() registered in the "advanced" command group.

  • Taskfile.yml:

    • Binary symlink path changed from $HOME/bin/ to $HOME/go/bin/.
    • New build-all (alias ba) task with -a flag for full rebuild.
    • New docs-llm-full task that generates docs/llm-full.txt from markdown sources in nav order (strips YAML front matter).
  • .gitignore: *.pyc, /*.log, .venv added.

  • pkg/teamloader/teamloader.go: Agent construction updated to use WithCompaction(agentConfig.Compaction) instead of WithNumHistoryItems. WithAddPromptScripts wired for the new field.

  • docs/index.md: Minor wording fix.

  • pkg/runtime/agent_delegation.go, pkg/runtime/fallback.go, pkg/runtime/model_picker.go, pkg/runtime/model_switcher.go, pkg/runtime/remote_runtime.go: Signature updates to accommodate the new AgentInfo() 5th parameter (instruction).

  • pkg/session/session_history_test.go: Import alignment.

Full Changelog: v1.36.0...v1.36.1