LLM Module¶
LLM client module.
- class atloop.llm.LLMClient(config: AtloopConfig, workspace_root: str | None = None)[source]¶
Bases:
objectLLM client wrapper with cache-optimized history management.
- __init__(config: AtloopConfig, workspace_root: str | None = None)[source]¶
Initialize LLM client.
- Parameters:
config – atloop configuration
workspace_root – Optional workspace root path for project skills
- add_tool_results_to_history(actions: List[Dict[str, Any]], results: List[Dict[str, Any]])[source]¶
Add tool execution results to conversation history.
NOTE: This method is kept for backward compatibility but does nothing since we no longer use ChatHistory. Tool results are stored in Memory and included in the next memory summary.
- Parameters:
actions – List of actions that were executed
results – List of tool execution results
- build_prompt(goal: str, constraints: List[str], budget: Dict[str, int], state_summary: str | None = None, project_profile: str | None = None, relevant_files: str | None = None, recent_error: str | None = None, current_diff: str | None = None, test_results: str | None = None, verification_success: bool | None = None) str[source]¶
Build complete prompt from templates (DEPRECATED - for backward compatibility).
This method is kept for backward compatibility but should be replaced with build_user_message() for cache optimization.
- Parameters:
goal – Task goal
constraints – Task constraints
budget – Budget dictionary
state_summary – State summary
project_profile – Project profile
relevant_files – Relevant file snippets
recent_error – Recent error
current_diff – Current diff
test_results – Test results
verification_success – Verification success status
- Returns:
Complete prompt string
- build_user_message(goal: str, constraints: List[str], budget: Dict[str, int], state_summary: str | None = None, project_profile: str | None = None, relevant_files: str | None = None, recent_error: str | None = None, current_diff: str | None = None, test_results: str | None = None, verification_success: bool | None = None) str[source]¶
Build user message from context (append-only mode for cache optimization).
This method builds a user message that will be appended to the conversation history. The system prompt is fixed and never changes, preserving LLM cache.
- Parameters:
goal – Task goal
constraints – Task constraints
budget – Budget dictionary
state_summary – State summary
project_profile – Project profile
relevant_files – Relevant file snippets
recent_error – Recent error
current_diff – Current diff
test_results – Test results
verification_success – Verification success status
- Returns:
User message string (to be appended to history)
- generate_tool_schema() str[source]¶
Generate tool schema description for prompt.
Automatically extracts descriptions from tool classes instead of hardcoding.
- Returns:
Tool schema description string
- get_skill_content(skill_name: str) str | None[source]¶
Get full skill content (Layer 2: full SKILL.md body).
This is called when the ‘skill’ tool is used. The content is returned as a tool result (user message), preserving cache.
- Parameters:
skill_name – Skill name
- Returns:
Full skill content, or None if skill not found
- load_prompt_template(template_name: str) str[source]¶
Load prompt template using PromptLoader.
- Parameters:
template_name – Template name (system, developer)
- Returns:
Template content
- plan_and_act(user_message: str, max_retries: int = 2, stream_callback: Callable[[str], None] | None = None) Tuple[ActionJSON | None, str | None, Dict[str, Any], str | None, Dict[str, str]][source]¶
Call LLM to plan and generate actions.
Memory-only mode (no ChatHistory): - Fixed system prompt (set once, never changes - preserves cache) - Each call is independent with full context in user_message - All history is managed through Memory, not conversation history - Uses lexilux 2.0.0 stream() for ensuring complete responses
- Parameters:
user_message – Required user message content containing all context (including memory summary)
max_retries – Maximum retry attempts if JSON parsing fails
stream_callback – Optional callback function to receive streaming output chunks
- Returns:
Tuple of (ActionJSON or None, error_message, usage_info, full_output_text, file_contents_dict) file_contents_dict maps placeholder names to actual file content
- class atloop.llm.ActionJSON(actions: List[Dict[str, Any]], stop_reason: str, thought_summary: str | None = None, plan: List[str] | None = None, result_message: str | None = None)[source]¶
Bases:
objectAction JSON data structure.
- __init__(actions: List[Dict[str, Any]], stop_reason: str, thought_summary: str | None = None, plan: List[str] | None = None, result_message: str | None = None)[source]¶
Initialize Action JSON.
- Parameters:
actions – List of action dictionaries
stop_reason – Stop reason (continue, done, fail)
thought_summary – Optional thought summary
plan – Optional plan steps
result_message – Optional result message
- atloop.llm.parse_action_json(text: str, max_retries: int = 2) Tuple[ActionJSON | None, str | None, Dict[str, str]][source]¶
Parse Action JSON from text with improved error handling.
Also extracts file contents from placeholders (FILE_CONTENT_#1, FILE_CONTENT_#2, etc.) that follow the JSON in the format: —(FILE_CONTENT_#1)— <file content> —(FILE_CONTENT_#2)— <file content> …
Tries multiple strategies: 1. Direct JSON parsing 2. Extract JSON from code blocks (
`json or `) 3. Extract JSON by matching braces (handling strings) 4. Fix common JSON errors 5. Use json-repair if available 6. Use json5 if available- Parameters:
text – Text containing JSON and optionally file contents
max_retries – Maximum number of retries (unused, kept for compatibility)
- Returns:
Tuple of (ActionJSON or None, error_message, file_contents_dict) file_contents_dict maps placeholder names (e.g., “FILE_CONTENT_#1”) to actual content
- atloop.llm.validate_action_json(data: Dict[str, Any]) Tuple[bool, str | None][source]¶
Validate Action JSON structure with detailed error messages.
- Parameters:
data – Action JSON dictionary
- Returns:
Tuple of (is_valid, error_message)
LLMClient¶
- class atloop.llm.client.LLMClient(config: AtloopConfig, workspace_root: str | None = None)[source]¶
Bases:
objectLLM client wrapper with cache-optimized history management.
- __init__(config: AtloopConfig, workspace_root: str | None = None)[source]¶
Initialize LLM client.
- Parameters:
config – atloop configuration
workspace_root – Optional workspace root path for project skills
- generate_tool_schema() str[source]¶
Generate tool schema description for prompt.
Automatically extracts descriptions from tool classes instead of hardcoding.
- Returns:
Tool schema description string
- get_skill_content(skill_name: str) str | None[source]¶
Get full skill content (Layer 2: full SKILL.md body).
This is called when the ‘skill’ tool is used. The content is returned as a tool result (user message), preserving cache.
- Parameters:
skill_name – Skill name
- Returns:
Full skill content, or None if skill not found
- load_prompt_template(template_name: str) str[source]¶
Load prompt template using PromptLoader.
- Parameters:
template_name – Template name (system, developer)
- Returns:
Template content
- build_user_message(goal: str, constraints: List[str], budget: Dict[str, int], state_summary: str | None = None, project_profile: str | None = None, relevant_files: str | None = None, recent_error: str | None = None, current_diff: str | None = None, test_results: str | None = None, verification_success: bool | None = None) str[source]¶
Build user message from context (append-only mode for cache optimization).
This method builds a user message that will be appended to the conversation history. The system prompt is fixed and never changes, preserving LLM cache.
- Parameters:
goal – Task goal
constraints – Task constraints
budget – Budget dictionary
state_summary – State summary
project_profile – Project profile
relevant_files – Relevant file snippets
recent_error – Recent error
current_diff – Current diff
test_results – Test results
verification_success – Verification success status
- Returns:
User message string (to be appended to history)
- build_prompt(goal: str, constraints: List[str], budget: Dict[str, int], state_summary: str | None = None, project_profile: str | None = None, relevant_files: str | None = None, recent_error: str | None = None, current_diff: str | None = None, test_results: str | None = None, verification_success: bool | None = None) str[source]¶
Build complete prompt from templates (DEPRECATED - for backward compatibility).
This method is kept for backward compatibility but should be replaced with build_user_message() for cache optimization.
- Parameters:
goal – Task goal
constraints – Task constraints
budget – Budget dictionary
state_summary – State summary
project_profile – Project profile
relevant_files – Relevant file snippets
recent_error – Recent error
current_diff – Current diff
test_results – Test results
verification_success – Verification success status
- Returns:
Complete prompt string
- plan_and_act(user_message: str, max_retries: int = 2, stream_callback: Callable[[str], None] | None = None) Tuple[ActionJSON | None, str | None, Dict[str, Any], str | None, Dict[str, str]][source]¶
Call LLM to plan and generate actions.
Memory-only mode (no ChatHistory): - Fixed system prompt (set once, never changes - preserves cache) - Each call is independent with full context in user_message - All history is managed through Memory, not conversation history - Uses lexilux 2.0.0 stream() for ensuring complete responses
- Parameters:
user_message – Required user message content containing all context (including memory summary)
max_retries – Maximum retry attempts if JSON parsing fails
stream_callback – Optional callback function to receive streaming output chunks
- Returns:
Tuple of (ActionJSON or None, error_message, usage_info, full_output_text, file_contents_dict) file_contents_dict maps placeholder names to actual file content
- reset_history()[source]¶
Reset conversation history (for new task).
NOTE: This method is kept for backward compatibility but does nothing since we no longer use ChatHistory. All history is managed through Memory.
- add_tool_results_to_history(actions: List[Dict[str, Any]], results: List[Dict[str, Any]])[source]¶
Add tool execution results to conversation history.
NOTE: This method is kept for backward compatibility but does nothing since we no longer use ChatHistory. Tool results are stored in Memory and included in the next memory summary.
- Parameters:
actions – List of actions that were executed
results – List of tool execution results
ActionJSON¶
- class atloop.llm.schema.ActionJSON(actions: List[Dict[str, Any]], stop_reason: str, thought_summary: str | None = None, plan: List[str] | None = None, result_message: str | None = None)[source]¶
Bases:
objectAction JSON data structure.
- __init__(actions: List[Dict[str, Any]], stop_reason: str, thought_summary: str | None = None, plan: List[str] | None = None, result_message: str | None = None)[source]¶
Initialize Action JSON.
- Parameters:
actions – List of action dictionaries
stop_reason – Stop reason (continue, done, fail)
thought_summary – Optional thought summary
plan – Optional plan steps
result_message – Optional result message