from stirling.config import AppSettings
from stirling.contracts import (
    AgentExecutionRequest,
    AgentSpec,
    AgentSpecStep,
    AiFile,
    EditPlanResponse,
    ExecutionContext,
    ExtractedFileText,
    ExtractedTextArtifact,
    OrchestratorRequest,
    PdfQuestionAnswerResponse,
    PdfTextSelection,
    ToolOperationStep,
)
from stirling.models import FileId
from stirling.models.tool_models import Angle, RotatePdfParams, ToolEndpoint


def test_orchestrator_request_accepts_user_message() -> None:
    request = OrchestratorRequest(
        user_message="Rotate the PDF",
        files=[AiFile(id=FileId("test-id"), name="test.pdf")],
        artifacts=[
            ExtractedTextArtifact(
                files=[
                    ExtractedFileText(
                        file_name="test.pdf",
                        pages=[PdfTextSelection(page_number=1, text="Hello")],
                    )
                ]
            )
        ],
    )

    assert request.user_message == "Rotate the PDF"
    assert len(request.artifacts) == 1


def test_agent_execution_request_uses_typed_agent_spec() -> None:
    steps: list[AgentSpecStep] = [
        ToolOperationStep(
            tool=ToolEndpoint.ROTATE_PDF,
            parameters=RotatePdfParams(angle=Angle(90)),
        )
    ]
    request = AgentExecutionRequest(
        agent_spec=AgentSpec(
            name="Invoice cleanup",
            description="Normalise inbound invoices",
            objective="Prepare uploads for accounting review",
            steps=steps,
        ),
        current_step_index=0,
        execution_context=ExecutionContext(input_files=["invoice.pdf"]),
    )

    assert request.agent_spec.steps[0].kind == "tool"


def test_edit_plan_response_has_typed_steps() -> None:
    steps = [ToolOperationStep(tool=ToolEndpoint.ROTATE_PDF, parameters=RotatePdfParams(angle=Angle(90)))]
    response = EditPlanResponse(
        summary="Rotate the input PDF by 90 degrees.",
        steps=steps,
    )

    assert response.steps[0].tool == ToolEndpoint.ROTATE_PDF


def test_pdf_question_answer_defaults_evidence_list() -> None:
    response = PdfQuestionAnswerResponse(answer="The invoice total is 120.00")

    assert response.evidence == []


def test_app_settings_accepts_model_configuration() -> None:
    from pathlib import Path

    from stirling.config import DocumentsBackend

    settings = AppSettings(
        smart_model_name="claude-sonnet-4-5-20250929",
        fast_model_name="claude-haiku-4-5-20251001",
        smart_model_max_tokens=8192,
        fast_model_max_tokens=2048,
        model_max_concurrency=32,
        documents_backend=DocumentsBackend.SQLITE,
        rag_embedding_model="voyageai:voyage-4",
        documents_sqlite_path=Path(":memory:"),
        documents_pgvector_dsn="",
        documents_pgvector_pool_min_size=1,
        documents_pgvector_pool_max_size=10,
        rag_chunk_size=512,
        rag_chunk_overlap=64,
        rag_default_top_k=5,
        rag_max_searches=5,
        chunked_reasoner_chars_per_slice=16_000,
        chunked_reasoner_concurrency=10,
        chunked_reasoner_worker_timeout_seconds=60.0,
        chunked_reasoner_notes_char_budget=250_000,
        max_pages=200,
        max_characters=200_000,
        require_user_id=False,
        posthog_enabled=False,
        posthog_api_key="",
        posthog_host="https://eu.i.posthog.com",
    )

    assert settings.smart_model_name
    assert settings.fast_model_max_tokens == 2048
