Documentation
¶
Overview ¶
Package chit provides conversation lifecycle management for LLM-powered chat applications.
Chit is a focused conversation controller that orchestrates pluggable processors for reasoning, action execution, and data retrieval. It handles turn-taking, session management, and response streaming.
Index ¶
- Variables
- func NewContinuationTerminal(cont Continuation) pipz.Chainable[*ChatRequest]
- func NewMiddleware(fn func(context.Context, *ChatRequest) (*ChatRequest, error)) pipz.Chainable[*ChatRequest]
- func NewTerminal(processor Processor) pipz.Chainable[*ChatRequest]
- func WithEmitter(ctx context.Context, e Emitter) context.Context
- type Chat
- type ChatProvider
- type ChatRequest
- type Config
- type Continuation
- type Emitter
- type Message
- type Option
- func WithBackoff(maxAttempts int, baseDelay time.Duration) Option
- func WithCircuitBreaker(failures int, recovery time.Duration) Option
- func WithConfig(config *Config) Option
- func WithErrorHandler(handler pipz.Chainable[*pipz.Error[*ChatRequest]]) Option
- func WithFallback(fallback ChatProvider) Option
- func WithHistory(history []Message) Option
- func WithMetadata(metadata map[string]any) Option
- func WithMiddleware(processors ...pipz.Chainable[*ChatRequest]) Option
- func WithRateLimit(rps float64, burst int) Option
- func WithRetry(maxAttempts int) Option
- func WithSystemPrompt(prompt string) Option
- func WithTimeout(duration time.Duration) Option
- type PipelineOption
- type Processor
- type ProcessorFunc
- type Resource
- type Response
- type Result
- type Yield
Constants ¶
This section is empty.
Variables ¶
var ( // ErrUnknownResultType is returned when a Processor returns a Result // that is neither a Response nor a Yield. ErrUnknownResultType = errors.New("chit: unknown result type") // ErrNilProcessor is returned when attempting to create a Chat without a Processor. ErrNilProcessor = errors.New("chit: processor is required") // ErrNilEmitter is returned when attempting to create a Chat without an Emitter. ErrNilEmitter = errors.New("chit: emitter is required") // ErrEmitterClosed is returned when attempting to emit after the Emitter is closed. ErrEmitterClosed = errors.New("chit: emitter is closed") )
Sentinel errors for chit operations.
var ( // Chat lifecycle signals. ChatCreated = capitan.NewSignal( "chit.chat.created", "New chat conversation initiated", ) // Input signals. InputReceived = capitan.NewSignal( "chit.input.received", "User input received for processing", ) // Processing signals. ProcessingStarted = capitan.NewSignal( "chit.processing.started", "Processor began handling input", ) ProcessingCompleted = capitan.NewSignal( "chit.processing.completed", "Processor finished handling input", ) ProcessingFailed = capitan.NewSignal( "chit.processing.failed", "Processor encountered an error", ) // Response signals. ResponseEmitted = capitan.NewSignal( "chit.response.emitted", "Response message emitted to client", ) // Resource signals. ResourcePushed = capitan.NewSignal( "chit.resource.pushed", "Structured resource pushed to client", ) // Turn management signals. TurnYielded = capitan.NewSignal( "chit.turn.yielded", "Processing yielded awaiting input", ) TurnResumed = capitan.NewSignal( "chit.turn.resumed", "Processing resumed from continuation", ) )
Signal definitions for chit conversation lifecycle events. Signals follow the pattern: chit.<entity>.<event>.
var ( // Chat metadata. FieldChatID = capitan.NewStringKey("chat_id") // Input metadata. FieldInput = capitan.NewStringKey("input") FieldInputSize = capitan.NewIntKey("input_size") // Processing metadata. FieldProcessingDuration = capitan.NewDurationKey("processing_duration") // Response metadata. FieldRole = capitan.NewStringKey("role") FieldContentSize = capitan.NewIntKey("content_size") // Resource metadata. FieldResourceType = capitan.NewStringKey("resource_type") FieldResourceURI = capitan.NewStringKey("resource_uri") // Turn metadata. FieldPrompt = capitan.NewStringKey("prompt") // Error information. FieldError = capitan.NewErrorKey("error") )
Field keys for chit event data.
Functions ¶
func NewContinuationTerminal ¶
func NewContinuationTerminal(cont Continuation) pipz.Chainable[*ChatRequest]
NewContinuationTerminal creates a terminal that calls the given continuation. Used to wrap continuation calls with the same reliability options as fresh calls.
func NewMiddleware ¶
func NewMiddleware(fn func(context.Context, *ChatRequest) (*ChatRequest, error)) pipz.Chainable[*ChatRequest]
NewMiddleware creates middleware from a callback function. The callback can inspect/modify the request or return an error to halt processing. For advanced use cases, create pipz processors directly and pass to WithMiddleware.
func NewTerminal ¶
func NewTerminal(processor Processor) pipz.Chainable[*ChatRequest]
NewTerminal creates the terminal processor that calls the Processor. This is the innermost layer of the pipeline that performs the actual processing.
Types ¶
type Chat ¶
type Chat struct {
// contains filtered or unexported fields
}
Chat is a conversation lifecycle controller. It orchestrates a pluggable Processor for reasoning and execution, manages turn-taking via continuations, and streams responses through an Emitter.
func New ¶
New creates a new Chat with the given processor and emitter. Both processor and emitter are required. Use functional options to configure the Chat further.
func (*Chat) GetPipeline ¶
func (c *Chat) GetPipeline() pipz.Chainable[*ChatRequest]
GetPipeline returns the internal pipeline for composition. This implements ChatProvider for use with WithFallback.
func (*Chat) Handle ¶
Handle processes user input through the conversation lifecycle.
The lifecycle is:
- Add user input to history
- If a continuation exists, resume with the input
- Otherwise, process the input through the pipeline
- Add response to history and emit via Emitter
- If result is a Yield, store the continuation for next input
func (*Chat) HasContinuation ¶
HasContinuation returns true if the Chat is awaiting input to resume a previously yielded processing step.
type ChatProvider ¶
type ChatProvider interface {
GetPipeline() pipz.Chainable[*ChatRequest]
}
ChatProvider is implemented by types that can provide a pipeline for composition.
type ChatRequest ¶
type ChatRequest struct {
// Input fields
Input string // User input to process
History []Message // User conversation history (read-only snapshot)
// Metadata fields
ChatID string // ID of the chat instance
RequestID string // Unique identifier for this request
// Output fields (populated by terminal)
Result Result // Processing result (Response or Yield)
}
ChatRequest flows through the pipz pipeline. It contains input, conversation history (read-only), metadata, and output fields.
func (*ChatRequest) Clone ¶
func (r *ChatRequest) Clone() *ChatRequest
Clone implements pipz.Cloner for concurrent middleware support.
type Config ¶
type Config struct {
// SystemPrompt is the system message that guides conversation behavior.
SystemPrompt string
// Metadata contains optional additional configuration data.
Metadata map[string]any
}
Config holds configuration for a Chat.
type Continuation ¶
Continuation is a function that resumes processing with new input. History provides the updated user conversation since the yield.
type Emitter ¶
type Emitter interface {
// Emit streams response content (conversational text) to the client.
Emit(ctx context.Context, msg Message) error
// Push sends structured resources synchronously to the client.
// Used for delivering fetched data, context, or tool results.
Push(ctx context.Context, resource Resource) error
// Close signals the end of output and releases resources.
Close() error
}
Emitter handles all output to the client. It supports both streaming response content and pushing structured resources.
func EmitterFromContext ¶
EmitterFromContext retrieves the Emitter from the context. Returns nil if no Emitter is present.
type Message ¶
type Message struct {
// Role identifies the message sender (e.g., "assistant", "system").
Role string
// Content is the text content of the message.
Content string
// Metadata contains optional additional information about the message.
Metadata map[string]any
}
Message is a streamed response unit in a conversation.
type Option ¶
type Option func(*Chat)
Option is a functional option for configuring a Chat.
func WithBackoff ¶
WithBackoff adds retry logic with exponential backoff to the pipeline. Failed requests are retried with increasing delays between attempts.
func WithCircuitBreaker ¶
WithCircuitBreaker adds circuit breaker protection to the pipeline. After 'failures' consecutive failures, the circuit opens for 'recovery' duration.
func WithConfig ¶
WithConfig sets the configuration for the Chat.
func WithErrorHandler ¶
WithErrorHandler adds error handling to the pipeline. The error handler receives error context and can process/log/alert as needed.
func WithFallback ¶
func WithFallback(fallback ChatProvider) Option
WithFallback adds a fallback chat for resilience. If the primary processor fails, the fallback will be tried.
func WithHistory ¶
WithHistory sets the initial conversation history for the Chat.
func WithMetadata ¶
WithMetadata sets metadata on the Chat's configuration.
func WithMiddleware ¶
func WithMiddleware(processors ...pipz.Chainable[*ChatRequest]) Option
WithMiddleware adds pre-processing steps before the terminal. Processors run in order, then the terminal (processor) runs.
func WithRateLimit ¶
WithRateLimit adds rate limiting to the pipeline. rps = requests per second, burst = burst capacity.
func WithRetry ¶
WithRetry adds retry logic to the pipeline. Failed requests are retried up to maxAttempts times.
func WithSystemPrompt ¶
WithSystemPrompt sets the system prompt for the Chat. This is a convenience option that creates a Config with the system prompt.
func WithTimeout ¶
WithTimeout adds timeout protection to the pipeline. Operations exceeding this duration will be canceled.
type PipelineOption ¶
type PipelineOption func(pipz.Chainable[*ChatRequest]) pipz.Chainable[*ChatRequest]
PipelineOption wraps a pipeline with additional behavior.
type Processor ¶
type Processor interface {
// Process handles user input and returns a result.
// History provides the user conversation for context (read-only).
// Returns a Response when complete, or a Yield when awaiting input.
Process(ctx context.Context, input string, history []Message) (Result, error)
}
Processor handles reasoning and execution logic for a conversation. It receives user input and conversation history (read-only) for context, and returns a Result. How the processor communicates with LLMs is an internal implementation detail.
type ProcessorFunc ¶
ProcessorFunc is an adapter that allows using a function as a Processor.
type Resource ¶
type Resource struct {
// Type identifies the kind of resource (e.g., "data", "context", "tool_result").
Type string
// URI is the scio URI if this resource was retrieved from a data source.
URI string
// Payload is the structured data being delivered.
Payload any
// Metadata contains optional additional information about the resource.
Metadata map[string]any
}
Resource is structured data pushed to the client. Used for delivering fetched data, context enrichment, or tool results.
type Response ¶
type Response struct {
// Content is the response text to emit.
Content string
// Metadata contains optional additional information about the response.
Metadata map[string]any
}
Response is a complete result with content to emit to the user.
func (*Response) IsComplete ¶
IsComplete returns true for Response.
type Result ¶
type Result interface {
// IsComplete returns true if processing finished with a response to emit.
IsComplete() bool
// IsYielded returns true if processing paused awaiting further input.
IsYielded() bool
}
Result represents the outcome of processing user input. A result is either complete (Response) or yielded (Yield).
type Yield ¶
type Yield struct {
// Prompt is the message to emit while awaiting input (e.g., a question).
Prompt string
// Continuation is the function to call with the next input to resume processing.
Continuation Continuation
// Metadata contains optional additional information about the yield.
Metadata map[string]any
}
Yield indicates processing has paused and is awaiting further input. The Continuation function resumes processing when input arrives.