Skip to main content

Module llm

Module llm 

Source
Expand description

LLM client abstraction (DOC-H3).

Provides a unified interface for different LLM providers including Anthropic Claude, OpenAI GPT, Ollama (local), and LM Studio (local).

§Supported Providers

ProviderClientEnvironment Variables
AnthropicAnthropicClientANTHROPIC_API_KEY
OpenAIOpenAiClientOPENAI_API_KEY
OllamaOllamaClientOLLAMA_HOST, OLLAMA_MODEL
LM StudioLmStudioClientLMSTUDIO_ENDPOINT, LMSTUDIO_MODEL

§Usage Examples

§Basic Completion

use subcog::llm::{LlmProvider, AnthropicClient};

let client = AnthropicClient::new();
let response = client.complete("Explain Rust ownership in one sentence")?;
println!("{response}");

§With System Prompt

use subcog::llm::{LlmProvider, OpenAiClient};

let client = OpenAiClient::new();
let response = client.complete_with_system(
    "You are a helpful coding assistant.",
    "How do I parse JSON in Rust?"
)?;

§Capture Analysis

use subcog::llm::{LlmProvider, OllamaClient};

let client = OllamaClient::new();
let analysis = client.analyze_for_capture(
    "Decision: Use PostgreSQL for the primary database due to JSONB support"
)?;

if analysis.should_capture && analysis.confidence > 0.8 {
    println!("Suggested namespace: {:?}", analysis.suggested_namespace);
    println!("Suggested tags: {:?}", analysis.suggested_tags);
}

§Resilient Provider with Circuit Breaker

use subcog::llm::{LlmProvider, AnthropicClient, ResilientLlmProvider, LlmResilienceConfig};

let base_client = AnthropicClient::new();
let resilient = ResilientLlmProvider::new(
    Box::new(base_client),
    LlmResilienceConfig::default()
);

// Automatically retries with exponential backoff and circuit breaker
let response = resilient.complete("Hello world")?;

§Configuration

Providers can be configured via environment variables or the config file:

[llm]
provider = "anthropic"  # or "openai", "ollama", "lmstudio"
model = "claude-sonnet-4-20250514"
timeout_ms = 30000
max_retries = 3

§Implementing a New Provider

To add a new LLM provider:

  1. Create a new module (e.g., src/llm/newprovider.rs)
  2. Implement the LlmProvider trait
  3. Export the client from this module

§Required Trait Methods

MethodPurpose
LlmProvider::nameReturn provider identifier (e.g., “anthropic”)
LlmProvider::completeGenerate completion for a prompt
LlmProvider::analyze_for_captureAnalyze content for memory capture

§Optional Methods (with defaults)

MethodDefault Behavior
complete_with_systemConcatenates system and user prompts
analyze_for_capture_extendedUses unified system prompt
classify_search_intentUses unified system prompt
analyze_for_consolidationUses unified system prompt

§Example Implementation

use subcog::llm::{LlmProvider, CaptureAnalysis};
use subcog::Result;

pub struct MyProvider {
    api_key: String,
    model: String,
}

impl LlmProvider for MyProvider {
    fn name(&self) -> &'static str {
        "myprovider"
    }

    fn complete(&self, prompt: &str) -> Result<String> {
        // Make API call to your provider
        todo!()
    }

    fn analyze_for_capture(&self, content: &str) -> Result<CaptureAnalysis> {
        // Use CAPTURE_ANALYSIS_PROMPT or custom prompt
        let prompt = format!(
            "{}\n\nContent: {content}",
            subcog::llm::CAPTURE_ANALYSIS_PROMPT
        );
        let response = self.complete(&prompt)?;
        // Parse JSON response into CaptureAnalysis
        todo!()
    }
}

§HTTP Client Guidelines

Use build_http_client with LlmHttpConfig for consistent timeout handling:

use subcog::llm::{build_http_client, LlmHttpConfig};

let config = LlmHttpConfig::from_env();
let client = build_http_client(config);

Re-exports§

pub use system_prompt::ArchiveCandidate;
pub use system_prompt::BASE_SYSTEM_PROMPT;
pub use system_prompt::CAPTURE_ANALYSIS_PROMPT;
pub use system_prompt::CONSOLIDATION_PROMPT;
pub use system_prompt::ConsolidationAnalysis;
pub use system_prompt::ContradictionAssessment;
pub use system_prompt::ContradictionDetail;
pub use system_prompt::ENRICHMENT_PROMPT;
pub use system_prompt::ExtendedCaptureAnalysis;
pub use system_prompt::ExtendedSearchIntent;
pub use system_prompt::MEMORY_SUMMARIZATION_PROMPT;
pub use system_prompt::MergeCandidate;
pub use system_prompt::OperationMode;
pub use system_prompt::SEARCH_INTENT_PROMPT;
pub use system_prompt::SecurityAssessment;
pub use system_prompt::build_system_prompt;
pub use system_prompt::build_system_prompt_with_config;

Modules§

anthropic 🔒
Anthropic Claude client.
lmstudio 🔒
LM Studio client.
ollama 🔒
Ollama (local) client.
openai 🔒
OpenAI client.
resilience 🔒
LLM resilience wrapper with circuit breaking and budget instrumentation.
system_prompt
Unified system prompt for subcog LLM operations.

Structs§

AnthropicClient
Anthropic Claude LLM client.
CaptureAnalysis
Analysis result for content capture.
LlmHttpConfig
HTTP client configuration for LLM providers.
LlmResilienceConfig
Resilience configuration for LLM calls.
LmStudioClient
LM Studio local LLM client.
OllamaClient
Ollama local LLM client.
OpenAiClient
OpenAI LLM client.
ResilientLlmProvider
LLM provider wrapper with circuit breaker and budget instrumentation.

Constants§

MAX_LLM_ERROR_RESPONSE_CHARS 🔒

Statics§

LLM_ERROR_REDACTOR 🔒

Traits§

LlmProvider
Trait for LLM providers.

Functions§

build_http_client
Builds a blocking HTTP client for LLM requests with configured timeouts.
extract_json_from_response
Extracts JSON from LLM response, handling markdown code blocks (CQ-H2).
parse_consolidation_analysis 🔒
Parses a consolidation analysis response from LLM output.
parse_extended_capture_analysis 🔒
Parses an extended capture analysis response from LLM output.
parse_extended_search_intent 🔒
Parses an extended search intent response from LLM output.
sanitize_llm_response_for_error 🔒