"""Poste.io mail server deployment playbook.

Defines the steps required to:
1. Perform initial setup via Playwright automation (configure hostname, create admin account)

Tenant servers must have stacks and env templates under /opt/letsbe.
"""

import uuid
from typing import Any
from urllib.parse import urlparse

from sqlalchemy.ext.asyncio import AsyncSession

from app.models.task import Task, TaskStatus


# LetsBe standard paths
POSTE_STACK_DIR = "/opt/letsbe/stacks/poste"


# =============================================================================
# Initial Setup via Playwright
# =============================================================================


def build_poste_initial_setup_step(
    *,
    base_url: str,
    admin_email: str,
    admin_password: str | None = None,
) -> dict[str, Any]:
    """
    Build a PLAYWRIGHT task payload for Poste.io initial setup.

    This configures the mail server hostname and creates the admin account
    on a fresh Poste.io installation.

    Args:
        base_url: The base URL for Poste.io (e.g., "https://mail.example.com")
        admin_email: Email address for the admin account (e.g., admin@example.com)
        admin_password: Password for the admin account (auto-generated if None)

    Returns:
        Task payload dict with type="PLAYWRIGHT"
    """
    # Extract domain from URL for allowlist
    parsed = urlparse(base_url)
    allowed_domain = parsed.netloc  # e.g., "mail.example.com"

    inputs: dict[str, Any] = {
        "base_url": base_url,
        "admin_email": admin_email,
    }

    # Only include password if provided - scenario will auto-generate if missing
    if admin_password:
        inputs["admin_password"] = admin_password

    return {
        "scenario": "poste_initial_setup",
        "inputs": inputs,
        "options": {
            "allowed_domains": [allowed_domain],
        },
        "timeout": 120,
    }


async def create_poste_initial_setup_task(
    *,
    db: AsyncSession,
    tenant_id: uuid.UUID,
    agent_id: uuid.UUID,
    base_url: str,
    admin_email: str,
    admin_password: str | None = None,
) -> Task:
    """
    Create and persist a PLAYWRIGHT task for Poste.io initial setup.

    Args:
        db: Async database session
        tenant_id: UUID of the tenant
        agent_id: UUID of the agent to assign the task to
        base_url: The base URL for Poste.io
        admin_email: Email address for the admin account
        admin_password: Password for admin (auto-generated if None)

    Returns:
        The created Task object with type="PLAYWRIGHT"
    """
    payload = build_poste_initial_setup_step(
        base_url=base_url,
        admin_email=admin_email,
        admin_password=admin_password,
    )

    task = Task(
        tenant_id=tenant_id,
        agent_id=agent_id,
        type="PLAYWRIGHT",
        payload=payload,
        status=TaskStatus.PENDING.value,
    )

    db.add(task)
    await db.commit()
    await db.refresh(task)

    return task
