Refactor cockpit to use DockerTmuxController pattern
Based on claude-code-tools TmuxCLIController, this refactor: - Added DockerTmuxController class for robust tmux session management - Implements send_keys() with configurable delay_enter - Implements capture_pane() for output retrieval - Implements wait_for_prompt() for pattern-based completion detection - Implements wait_for_idle() for content-hash-based idle detection - Implements wait_for_shell_prompt() for shell prompt detection Also includes workflow improvements: - Pre-task git snapshot before agent execution - Post-task commit protocol in agent guidelines Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
126
lib/luzia_cli_integration.py
Executable file
126
lib/luzia_cli_integration.py
Executable file
@@ -0,0 +1,126 @@
|
||||
"""
|
||||
Luzia CLI Integration - Bridge between luzia dispatcher and new 4-bucket context system.
|
||||
This module replaces the old get_project_context() implementation with the modernized version.
|
||||
"""
|
||||
|
||||
import sys
|
||||
import os
|
||||
from pathlib import Path
|
||||
import logging
|
||||
|
||||
logging.basicConfig(level=logging.INFO, format='%(message)s')
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
def get_project_context_modernized(project: str, config: dict, task_query: str = "", use_new_retriever: bool = True) -> str:
|
||||
"""
|
||||
NEW: Get project context using 4-bucket modernized system.
|
||||
|
||||
Falls back to legacy system if modernization fails.
|
||||
|
||||
Args:
|
||||
project: Project name
|
||||
config: luzia config dict
|
||||
task_query: Optional task query for better context retrieval
|
||||
use_new_retriever: If False, use legacy system
|
||||
|
||||
Returns:
|
||||
Formatted context string for prompt injection
|
||||
"""
|
||||
|
||||
# Attempt modernized retrieval
|
||||
if use_new_retriever:
|
||||
try:
|
||||
sys.path.insert(0, os.path.dirname(__file__))
|
||||
from four_bucket_context import assemble_prompt_context
|
||||
|
||||
project_config = config["projects"].get(project, {})
|
||||
project_path = project_config.get("path", f"/home/{project}")
|
||||
user = project # By convention, project user matches project name
|
||||
cwd = project_path
|
||||
|
||||
# Use task query if provided, otherwise use project name
|
||||
query = task_query if task_query else f"Working on {project} project"
|
||||
|
||||
context = assemble_prompt_context(query, project, user, cwd)
|
||||
logger.debug(f"✓ Using modernized 4-bucket context ({len(context)} chars)")
|
||||
return context
|
||||
|
||||
except Exception as e:
|
||||
logger.debug(f"Modernized retriever failed: {e}")
|
||||
logger.debug("Falling back to legacy system...")
|
||||
|
||||
# Fall back to legacy implementation
|
||||
return get_project_context_legacy(project, config)
|
||||
|
||||
|
||||
def get_project_context_legacy(project: str, config: dict) -> str:
|
||||
"""
|
||||
LEGACY: Original get_project_context implementation.
|
||||
Kept for backward compatibility and as fallback.
|
||||
"""
|
||||
|
||||
project_config = config["projects"].get(project, {})
|
||||
|
||||
context_parts = [
|
||||
f"You are working on the **{project}** project.",
|
||||
f"Description: {project_config.get('description', 'Project user')}",
|
||||
f"Focus: {project_config.get('focus', 'General development')}",
|
||||
"",
|
||||
"**IMPORTANT**: All commands execute inside a Docker container as the project user.",
|
||||
"Files you create/modify will be owned by the correct user.",
|
||||
"Working directory: /workspace (mounted from project home)",
|
||||
""
|
||||
]
|
||||
|
||||
# Try to load project CLAUDE.md
|
||||
project_path = project_config.get("path", f"/home/{project}")
|
||||
claude_md = Path(project_path) / "CLAUDE.md"
|
||||
|
||||
if claude_md.exists():
|
||||
try:
|
||||
with open(claude_md) as f:
|
||||
context_parts.append("## Project Guidelines (from CLAUDE.md):")
|
||||
context_parts.append(f.read())
|
||||
except:
|
||||
pass
|
||||
|
||||
# Legacy KG search
|
||||
try:
|
||||
sys.path.insert(0, os.path.dirname(__file__))
|
||||
# Import old _search_project_kg (if available)
|
||||
# For now, just skip this if not available
|
||||
pass
|
||||
except:
|
||||
pass
|
||||
|
||||
return "\n".join(context_parts)
|
||||
|
||||
|
||||
def should_use_new_retriever(args_list: list) -> bool:
|
||||
"""Check if --disable-new-retriever flag is present."""
|
||||
return "--disable-new-retriever" not in args_list
|
||||
|
||||
|
||||
# Integration marker for documentation
|
||||
INTEGRATION_PATCH = """
|
||||
INTEGRATION PATCH for luzia CLI
|
||||
================================
|
||||
|
||||
Replace the get_project_context() function in /opt/server-agents/orchestrator/bin/luzia
|
||||
with this call:
|
||||
|
||||
from luzia_cli_integration import get_project_context_modernized, should_use_new_retriever
|
||||
|
||||
# In the dispatch function, replace:
|
||||
# context = get_project_context(project, config)
|
||||
# With:
|
||||
# use_new = should_use_new_retriever(sys.argv)
|
||||
# context = get_project_context_modernized(project, config, task_query, use_new_retriever=use_new)
|
||||
|
||||
Changes are backward-compatible and include graceful fallback to legacy system.
|
||||
"""
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
print(INTEGRATION_PATCH)
|
||||
Reference in New Issue
Block a user