Documentation
¶
Index ¶
Constants ¶
const MaxJSONLLineSize = 10 * 1024 * 1024 // 10MB
MaxJSONLLineSize is the maximum size for a single JSONL line Default bufio.Scanner buffer is 64KB, but transcript lines with thinking blocks and tool results can exceed 1MB
const MaxMetadataFieldLength = 8 * 1024 // 8KB
MaxMetadataFieldLength is the maximum byte length for provider session metadata fields (first_user_message, summary) sent to the backend. Callers should use MaxMetadataFieldLength/2 (4KB) for first_user_message to leave headroom for JSON serialization overhead below the backend's 8192-character limit.
Variables ¶
This section is empty.
Functions ¶
func NewJSONLScanner ¶
NewJSONLScanner creates a bufio.Scanner configured for large JSONL files with a 10MB buffer to handle long transcript lines
func ValidateSessionID ¶ added in v0.15.0
ValidateSessionID checks that a session ID contains only safe characters.
Types ¶
type ClaudeHookInput ¶ added in v0.16.0
type ClaudeHookInput struct {
SessionID string `json:"session_id"`
TranscriptPath string `json:"transcript_path"`
CWD string `json:"cwd"`
PermissionMode string `json:"permission_mode"`
HookEventName string `json:"hook_event_name"`
Reason string `json:"reason"`
ParentPID int `json:"parent_pid,omitempty"` // Claude Code process ID (set by confab, not Claude Code)
// UserPromptSubmit-specific fields
Prompt string `json:"prompt,omitempty"`
// PreToolUse/PostToolUse-specific fields
ToolName string `json:"tool_name,omitempty"`
ToolInput map[string]any `json:"tool_input,omitempty"`
ToolUseID string `json:"tool_use_id,omitempty"`
ToolResponse map[string]any `json:"tool_response,omitempty"` // PostToolUse only
}
ClaudeHookInput represents hook data from Claude Code.
This is a union type containing fields from all hook types (SessionStart, UserPromptSubmit, PreToolUse, PostToolUse, etc.). JSON unmarshaling handles missing fields gracefully. This approach is pragmatic for a small number of hooks with mostly orthogonal fields. Consider splitting into separate types if hooks start having conflicting field semantics or the number of hook types grows significantly.
func ReadClaudeHookInput ¶ added in v0.16.0
func ReadClaudeHookInput(r io.Reader) (*ClaudeHookInput, error)
ReadClaudeHookInput reads and parses hook input JSON from a reader. Used by PreToolUse, PostToolUse, and other hook handlers.
type ClaudeHookResponse ¶ added in v0.16.0
type ClaudeHookResponse struct {
Continue bool `json:"continue"`
StopReason string `json:"stopReason"`
SuppressOutput bool `json:"suppressOutput"`
SystemMessage string `json:"systemMessage,omitempty"`
}
ClaudeHookResponse is the JSON response sent back to Claude Code
type CodexHookInput ¶ added in v0.16.0
type CodexHookInput struct {
SessionID string `json:"session_id"`
TranscriptPath string `json:"transcript_path"`
CWD string `json:"cwd"`
HookEventName string `json:"hook_event_name"`
Model string `json:"model,omitempty"`
Source string `json:"source,omitempty"`
TurnID string `json:"turn_id,omitempty"`
ParentPID int `json:"parent_pid,omitempty"` // Codex process ID (set by confab, not Codex)
// PreToolUse/PostToolUse-specific fields. Codex normalizes its shell
// tool's tool_name to "Bash" in hook stdin (HookToolName::bash() in
// codex-rs/core/src/tools/hook_names.rs), so our Bash matcher and
// gitCommit/ghPRCreate regexes work without per-provider tweaks.
//
// ToolResponse is json.RawMessage rather than map[string]any because
// Codex's PostToolUse schema types tool_response as `any` JSON value:
// the shell tool emits a plain JSON string (the aggregated exec output
// from format_exec_output_str), while other tools emit objects. Use
// ToolResponseMap to get a normalized map[string]any for either shape.
ToolName string `json:"tool_name,omitempty"`
ToolInput map[string]any `json:"tool_input,omitempty"`
ToolUseID string `json:"tool_use_id,omitempty"`
ToolResponse json.RawMessage `json:"tool_response,omitempty"` // PostToolUse only
}
CodexHookInput contains the shared fields Confab needs from Codex command hooks. The fields follow the current official Codex hook schemas, while provider-specific parsing owns validation. Like ClaudeHookInput, this is a union type carrying fields from all Codex hook events (SessionStart, PreToolUse, PostToolUse); JSON unmarshaling handles missing fields gracefully.
func (*CodexHookInput) ToolResponseMap ¶ added in v0.16.1
func (c *CodexHookInput) ToolResponseMap() map[string]any
ToolResponseMap normalizes the Codex tool_response value into a map[string]any so downstream provider-agnostic code can use a single shape. Codex's shell tool sends a plain string; other tools send objects. Strings get wrapped under "stdout" because that's how our PR-URL extractor and success heuristics read shell output.
type CodexHookResponse ¶ added in v0.16.0
type CodexHookResponse struct {
Continue bool `json:"continue"`
StopReason string `json:"stopReason,omitempty"`
SystemMessage string `json:"systemMessage,omitempty"`
SuppressOutput bool `json:"suppressOutput,omitempty"`
}
CodexHookResponse is the JSON response sent back to Codex hooks.
type InboxEvent ¶
type InboxEvent struct {
Type string `json:"type"` // Event type: "session_end"
Timestamp time.Time `json:"timestamp"` // When the event was written
HookInput *ClaudeHookInput `json:"hook_input,omitempty"` // Full hook payload for session events
}
InboxEvent represents an event written to the daemon's inbox file. The inbox is a JSONL file where each line is an event.
type OpenCodeHookInput ¶ added in v0.17.0
type OpenCodeHookInput struct {
SessionID string `json:"session_id"`
CWD string `json:"cwd"`
ParentPID int `json:"parent_pid,omitempty"`
// ParentID is the OpenCode session's parent session id, set by the plugin
// only for subagent (non-root) sessions. Used to suppress daemons for
// non-root sessions (CF-537); root sessions omit it. Distinct from
// ParentPID, which is an OS process id.
ParentID string `json:"parent_id,omitempty"`
}
OpenCodeHookInput represents hook data from OpenCode. Unlike Claude/Codex, OpenCode doesn't pipe hook data via stdin from a settings-file hook system. Instead, the TypeScript plugin constructs this struct from the event payload and passes it via stdin to the confab hook commands. The daemon then reads OpenCode session data directly from the local SQLite DB at ~/.local/share/opencode/opencode.db (or CONFAB_OPENCODE_DB), so no per-session URL is required.
type PreToolUseOutput ¶
type PreToolUseOutput struct {
HookEventName string `json:"hookEventName"`
PermissionDecision string `json:"permissionDecision,omitempty"` // "allow", "deny", or "ask"
PermissionDecisionReason string `json:"permissionDecisionReason,omitempty"`
}
PreToolUseOutput contains PreToolUse-specific decision fields.
type PreToolUseResponse ¶
type PreToolUseResponse struct {
HookSpecificOutput *PreToolUseOutput `json:"hookSpecificOutput,omitempty"`
}
PreToolUseResponse is the JSON response for PreToolUse hooks. The shape is provider-agnostic: Claude Code and Codex both accept the same hookSpecificOutput.permissionDecision contract per their respective schemas.