This repository has been archived on 2026-08-16. You can view files and clone it, but cannot push or open issues or pull requests.
ollie-core/session/session.go

188 lines
6.4 KiB
Go

package session
import (
"context"
"errors"
"github.com/simonfxr/pubsub"
"ollie/backend"
)
// WatchField names supported by Core.WaitChange.
const (
WatchState = "state"
WatchUsage = "usage"
WatchCtxSz = "ctxsz"
WatchCWD = "cwd"
WatchAgent = "agent"
)
// ErrInterrupted is returned when the user cancels an agent turn (Ctrl-C).
var ErrInterrupted = errors.New("interrupted")
// Event is a typed output event emitted during an agent turn or in response
// to a command.
type Event struct {
Role string
Name string
Content string
ResponseID string
}
// EventHandler receives events from the agent.
type EventHandler func(Event)
// Session is the interface between a frontend (TUI, HTTP handler, etc.) and the
// agent engine. All output from the agent is delivered via the event bus.
type Session interface {
// Submit processes one line of user input. Slash commands and shell
// shortcuts are dispatched synchronously; any other input starts an agent
// turn that publishes events to the bus until the turn is complete.
// After the turn, any queued prompts are drained sequentially.
Submit(ctx context.Context, input string)
// Interrupt cancels the current in-progress agent turn.
// Returns true if an action was running and was cancelled.
Interrupt(cause error) bool
// Inject sends a message that will be appended to the next tool result
// as a user interruption. If no turn is running, it is silently dropped.
Inject(prompt string)
// Queue pushes a prompt onto the FIFO for execution after the current
// turn completes.
Queue(prompt string)
// Bus returns the session event bus.
Bus() *pubsub.Bus
// PopQueue removes and returns the next queued prompt.
// Returns ("", false) if the queue is empty.
PopQueue() (string, bool)
// IsRunning returns true if an agent turn is currently in progress.
IsRunning() bool
// State returns the current agent state: "idle", "thinking", or "calling: <tool>".
State() string
// Reply returns the assistant text from the most recently completed turn.
// Cleared when a new prompt is submitted.
Reply() string
// AgentName returns the name of the active agent.
AgentName() string
// BackendName returns the name of the active backend (e.g. "anthropic", "ollama").
BackendName() string
// ModelName returns the name of the active model.
ModelName() string
// CtxSz returns the estimated context size as a one-line summary.
CtxSz() string
// Usage returns billed token counts as a one-line summary.
Usage() string
// Cost returns per-turn and session cost as a two-line key=value summary.
Cost() string
// ListModels returns available model names, one per line.
ListModels() string
// CWD returns the current working directory used for tool execution.
CWD() string
// SetCWD changes the working directory for tool execution and
// updates the system prompt. Returns an error if the path does not exist.
SetCWD(dir string) error
// SetSessionID renames the session: updates the in-memory ID, renames
// persisted files on disk, and propagates to the execute server env.
SetSessionID(newID string) error
// Context returns the current message history as it would be sent to the
// backend: system prompt prepended, stale reads pruned. Does not include
// tool definitions (see Tools) or generation params (see GenerationParams).
Context() []backend.Message
// SystemPrompt returns the fully rendered system prompt for this session.
SystemPrompt() string
// GenerationParams returns the current sampling parameters.
GenerationParams() backend.GenerationParams
// SetGenerationParams replaces the current sampling parameters.
// Returns an error if the agent is currently running.
SetGenerationParams(params backend.GenerationParams) error
// CompactionModel returns the model override used for context compaction.
CompactionModel() string
// SetCompactionModel changes the model used for context compaction.
SetCompactionModel(model string)
// SetEnv injects a session-scoped environment variable into the shell
// subprocesses. Does not affect the daemon process environment.
SetEnv(key, value string)
// WaitChange blocks until the named field changes from current, then returns
// the new value. Returns ("", false) if ctx is cancelled before a change.
// Supported fields: WatchState, WatchUsage, WatchCtxSz, WatchCWD.
WaitChange(ctx context.Context, field, current string) (string, bool)
// ToolCallCount returns the total number of tool calls executed in this
// session since the agent was created. The counter is monotonically
// increasing and never resets. Blocked calls (pre-tool hook exit 2) are
// not counted. Timed-out or erroring calls are counted because execution
// was attempted. Use modulo arithmetic in hooks to fire every N calls:
// [ $(($(cat tcct) % 10)) -eq 0 ] && ...
ToolCallCount() int64
// SaveSession writes the current session state to the given path.
// The file includes all messages, agent/backend/model metadata, and task state.
SaveSession(path string) error
// Close releases resources associated with the session, including its
// temporary directory under /tmp/ollie/.
Close()
// Detach detaches the currently running process from the agent.
// The process continues running; returns false if nothing is executing.
Detach() bool
// ListDetached returns info about all detached processes.
ListDetached() []DetachedInfo
// SignalDetached sends a signal to a detached process by PID.
SignalDetached(pid, signal int) error
// GetDetachedOutput returns the ring buffer output for a detached process.
GetDetachedOutput(pid int) (string, error)
// DismissDetached removes an exited process from the list.
DismissDetached(pid int) bool
// InjectSystemEvent appends a system-originated message to the session
// context and emits it on the event bus. The agent sees it on its next
// turn; it appears in the chat log immediately.
InjectSystemEvent(content string)
// React records an emoji reaction to the most recent assistant response.
React(emoji string)
// ReactTo records an emoji reaction to a specific assistant response.
ReactTo(responseID, emoji string) error
// Reactions returns the current response ID to emoji mapping.
Reactions() map[string]string
}
// DetachedInfo describes a detached process for external consumers.
type DetachedInfo struct {
PID int
Command string
Started int64 // unix timestamp
Exited bool
ExitCode int
}