#!/usr/bin/env python3

from src.alloy.lexer import AlloyLexer
from src.alloy.parser import AlloyParser
from src.alloy.interpreter import Interpreter

def detailed_test(test_name, code):
    """Run detailed analysis of a test case"""
    print(f"\n{'='*60}")
    print(f"TEST: {test_name}")
    print(f"{'='*60}")
    print(f"Code:\n{code}")
    print("-" * 40)
    
    lexer = AlloyLexer()
    parser = AlloyParser(lexer)
    
    # First, let's tokenize to see what tokens we get
    lexer.lexer.input(code)
    print("Tokens:")
    tokens = []
    for tok in lexer.lexer:
        tokens.append(f"{tok.type}({tok.value})")
        if len(tokens) % 5 == 0:
            print("  ", " ".join(tokens[-5:]))
    if len(tokens) % 5 != 0:
        print("  ", " ".join(tokens[-(len(tokens) % 5):]))
    
    print("\n" + "-" * 40)
    
    # Now parse
    try:
        ast = parser.parse(code)
        print(f"AST: {ast}")
    except Exception as e:
        print(f"Parse error: {e}")
        return
    
    print("\n" + "-" * 40)
    
    # Try to interpret
    interpreter = Interpreter()
    try:
        result = interpreter.interpret(ast)
        print(f"Execution successful")
        print(f"Global env vars: {list(interpreter.global_env.vars.keys())}")
    except Exception as e:
        print(f"Runtime error: {e}")

# Test 1: alloy agent builtin
detailed_test("test_alloy_agent_builtin", '''
command Review means "review the provided code for improvements"
code_review = alloy Review "tool_code"
''')

# Test 2: data processing pipeline (simplified)
detailed_test("test_data_processing_pipeline (simplified)", '''
raw_data = "sales_csv_data"
''')

# Test 3: tool with multiple statements
detailed_test("test_tool_with_multiple_statements", '''
tool process_order takes order returns order_result {
    tax_amount = order + 0.08
    total = order + tax_amount
    order_result = {
        subtotal: order,
        tax: tax_amount,
        total: total
    }
}
result = process_order(100)
''')

# Test 4: then chaining agent to tool
detailed_test("test_then_chaining_agent_to_tool", '''
command Research means "research the provided topic"
tool process_analysis takes analysis returns result {
    result = "Processed: " + analysis
}

claude = agent "claude-3.5-sonnet"

final_result, error = claude Research "AI trends" then process_analysis
''')

# Test 5: then chaining with nested calls
detailed_test("test_then_chaining_with_nested_calls", '''
tool inner_tool takes x returns result {
    result = x + "_inner"
}

tool outer_tool takes x returns result {
    inner_result, inner_error = inner_tool(x)
    when inner_error then {
        result = (null, inner_error)
    } otherwise {
        result = inner_result + "_outer"
    }
}

tool final_tool takes x returns result {
    result = x + "_final"
}

final_result, error = outer_tool("start") then final_tool
''')

# Test 6: agent block in chain
detailed_test("test_agent_block_in_chain", '''
command Analyze means "analyze the provided data and return insights"

tool prepare_text takes text returns result {
    result = text + " (prepared for analysis)"
}

claude = agent "gpt-4o-mini"

final_result, error = prepare_text("hello") then claude {
    must Analyze
}
''')

# Test 7: agent block multiple variables
detailed_test("test_agent_block_multiple_variables", '''
command CreateUserProfile means "create a comprehensive user profile"
command IncludeUserDetails means "include specific user details in the profile"

claude = agent "gpt-4o-mini"
user_name = "Alice"
user_age = 25
user_occupation = "Engineer"

result, error = claude {
    must CreateUserProfile
    should IncludeUserDetails user_name
}
''')