"""TES v1.1 API client."""

from __future__ import annotations

from typing import Any

from ai4gh.core.client import GA4GHClient
from ai4gh.specs.tes.models import (
    TESCreateTaskResponse,
    TESListTasksResponse,
    TESTask,
    TESView,
)


class TESClient(GA4GHClient):
    """Client for the GA4GH Task Execution Service (TES) v1.1.

    TES provides a standard API for submitting batch tasks with
    defined inputs, outputs, and executor commands.
    """

    spec_name = "tes"
    spec_version = "1.1.0"
    base_path = "/ga4gh/tes/v1"

    async def create_task(self, task: dict[str, Any]) -> TESCreateTaskResponse:
        """Create a new TES task.

        Args:
            task: The task definition dict.

        Returns:
            A response with the new task ID.
        """
        data = await self._request("POST", "/tasks", json=task)
        return TESCreateTaskResponse.model_validate(data)

    async def get_task(
        self,
        task_id: str,
        *,
        view: TESView = TESView.MINIMAL,
    ) -> TESTask:
        """Get a task by ID.

        Args:
            task_id: The task identifier.
            view: Detail level (MINIMAL, BASIC, FULL).

        Returns:
            The task with the requested level of detail.
        """
        params: dict[str, Any] = {"view": view.value}
        data = await self._request("GET", f"/tasks/{task_id}", params=params)
        return TESTask.model_validate(data)

    async def list_tasks(
        self,
        *,
        view: TESView = TESView.MINIMAL,
        page_size: int | None = None,
        page_token: str | None = None,
        name_prefix: str | None = None,
        state: str | None = None,
        tag_key: str | None = None,
        tag_value: str | None = None,
    ) -> TESListTasksResponse:
        """List tasks.

        Args:
            view: Detail level for listed tasks.
            page_size: Maximum number of tasks to return.
            page_token: Token for pagination.
            name_prefix: Filter by task name prefix.
            state: Filter by task state.
            tag_key: Filter by tag key.
            tag_value: Filter by tag value (requires tag_key).

        Returns:
            List of tasks with optional pagination token.
        """
        params: dict[str, Any] = {"view": view.value}
        if page_size is not None:
            params["page_size"] = page_size
        if page_token is not None:
            params["page_token"] = page_token
        if name_prefix is not None:
            params["name_prefix"] = name_prefix
        if state is not None:
            params["state"] = state
        if tag_key is not None:
            params["tag_key"] = tag_key
        if tag_value is not None:
            params["tag_value"] = tag_value
        data = await self._request("GET", "/tasks", params=params)
        return TESListTasksResponse.model_validate(data)

    async def cancel_task(self, task_id: str) -> dict[str, Any]:
        """Cancel a running task.

        Args:
            task_id: The task identifier.

        Returns:
            Empty dict on success.
        """
        data: dict[str, Any] = await self._request("POST", f"/tasks/{task_id}:cancel")
        return data
