# app/modules/messaging/routes/api/store_email_templates.py
"""
Store email template override endpoints.

Allows stores to customize platform email templates with their own content.
Platform-only templates (billing, subscription) cannot be overridden.

Store Context: Uses token_store_id from JWT token (authenticated store API pattern).
"""

import logging
from typing import Any

from fastapi import APIRouter, Depends
from pydantic import BaseModel, EmailStr, Field
from sqlalchemy.orm import Session

from app.api.deps import get_current_store_api
from app.core.database import get_db
from app.modules.messaging.services.email_service import EmailService
from app.modules.messaging.services.email_template_service import EmailTemplateService
from app.modules.tenancy.schemas.auth import UserContext
from app.modules.tenancy.services.store_service import store_service

store_email_templates_router = APIRouter(prefix="/email-templates")
logger = logging.getLogger(__name__)


# =============================================================================
# SCHEMAS
# =============================================================================


class StoreTemplateUpdate(BaseModel):
    """Schema for creating/updating a store template override."""

    subject: str = Field(..., min_length=1, max_length=500)
    body_html: str = Field(..., min_length=1)
    body_text: str | None = None
    name: str | None = Field(None, max_length=255)


class TemplatePreviewRequest(BaseModel):
    """Schema for previewing a template."""

    language: str = "en"
    variables: dict[str, Any] = {}


class TemplateTestRequest(BaseModel):
    """Schema for sending a test email."""

    to_email: EmailStr
    language: str = "en"
    variables: dict[str, Any] = {}


# =============================================================================
# ENDPOINTS
# =============================================================================


@store_email_templates_router.get("")
def list_overridable_templates(
    current_user: UserContext = Depends(get_current_store_api),
    db: Session = Depends(get_db),
):
    """
    List all email templates that the store can customize.

    Returns platform templates with store override status.
    Platform-only templates (billing, subscription) are excluded.
    """
    store_id = current_user.token_store_id
    service = EmailTemplateService(db)
    return service.list_overridable_templates(store_id)


@store_email_templates_router.get("/{code}")
def get_template(
    code: str,
    current_user: UserContext = Depends(get_current_store_api),
    db: Session = Depends(get_db),
):
    """
    Get a specific template with all language versions.

    Returns platform template details and store overrides for each language.
    """
    store_id = current_user.token_store_id
    service = EmailTemplateService(db)
    return service.get_store_template(store_id, code)


@store_email_templates_router.get("/{code}/{language}")
def get_template_language(
    code: str,
    language: str,
    current_user: UserContext = Depends(get_current_store_api),
    db: Session = Depends(get_db),
):
    """
    Get a specific template for a specific language.

    Returns store override if exists, otherwise platform template.
    """
    store_id = current_user.token_store_id
    service = EmailTemplateService(db)
    return service.get_store_template_language(store_id, code, language)


@store_email_templates_router.put("/{code}/{language}")
def update_template_override(
    code: str,
    language: str,
    template_data: StoreTemplateUpdate,
    current_user: UserContext = Depends(get_current_store_api),
    db: Session = Depends(get_db),
):
    """
    Create or update a store template override.

    Creates a store-specific version of the email template.
    The platform template remains unchanged.
    """
    store_id = current_user.token_store_id
    service = EmailTemplateService(db)

    result = service.create_or_update_store_override(
        store_id=store_id,
        code=code,
        language=language,
        subject=template_data.subject,
        body_html=template_data.body_html,
        body_text=template_data.body_text,
        name=template_data.name,
    )
    db.commit()

    return result


@store_email_templates_router.delete("/{code}/{language}")
def delete_template_override(
    code: str,
    language: str,
    current_user: UserContext = Depends(get_current_store_api),
    db: Session = Depends(get_db),
):
    """
    Delete a store template override.

    Reverts to using the platform default template for this language.
    """
    store_id = current_user.token_store_id
    service = EmailTemplateService(db)
    service.delete_store_override(store_id, code, language)
    db.commit()

    return {
        "message": "Template override deleted - reverted to platform default",
        "code": code,
        "language": language,
    }


@store_email_templates_router.post("/{code}/preview")
def preview_template(
    code: str,
    preview_data: TemplatePreviewRequest,
    current_user: UserContext = Depends(get_current_store_api),
    db: Session = Depends(get_db),
):
    """
    Preview a template with sample variables.

    Uses store override if exists, otherwise platform template.
    """
    store_id = current_user.token_store_id
    store = store_service.get_store_by_id(db, store_id)
    service = EmailTemplateService(db)

    # Add branding variables
    variables = {
        **_get_sample_variables(code),
        **preview_data.variables,
        "platform_name": "Orion",
        "store_name": store.name if store else "Your Store",
        "support_email": store.contact_email if store else "support@orion.lu",
    }

    return service.preview_store_template(
        store_id=store_id,
        code=code,
        language=preview_data.language,
        variables=variables,
    )


@store_email_templates_router.post("/{code}/test")
def send_test_email(
    code: str,
    test_data: TemplateTestRequest,
    current_user: UserContext = Depends(get_current_store_api),
    db: Session = Depends(get_db),
):
    """
    Send a test email using the template.

    Uses store override if exists, otherwise platform template.
    """
    store_id = current_user.token_store_id
    store = store_service.get_store_by_id(db, store_id)

    # Build test variables
    variables = {
        **_get_sample_variables(code),
        **test_data.variables,
        "platform_name": "Orion",
        "store_name": store.name if store else "Your Store",
        "support_email": store.contact_email if store else "support@orion.lu",
    }

    try:
        email_svc = EmailService(db)
        email_log = email_svc.send_template(
            template_code=code,
            to_email=test_data.to_email,
            variables=variables,
            store_id=store_id,
            language=test_data.language,
        )

        if email_log.status == "sent":
            return {
                "success": True,
                "message": f"Test email sent to {test_data.to_email}",
            }
        return {
            "success": False,
            "message": email_log.error_message or "Failed to send email",
        }
    except Exception as e:
        logger.exception(f"Failed to send test email: {e}")
        return {
            "success": False,
            "message": str(e),
        }


# =============================================================================
# HELPERS
# =============================================================================


def _get_sample_variables(template_code: str) -> dict[str, Any]:
    """Get sample variables for testing templates."""
    samples = {
        "signup_welcome": {
            "first_name": "John",
            "merchant_name": "Acme Corp",
            "email": "john@example.com",
            "store_code": "acme",
            "login_url": "https://example.com/login",
            "trial_days": "14",
            "tier_name": "Business",
        },
        "order_confirmation": {
            "customer_name": "Jane Doe",
            "order_number": "ORD-12345",
            "order_total": "€99.99",
            "order_items_count": "3",
            "order_date": "2024-01-15",
            "shipping_address": "123 Main St, Luxembourg City, L-1234",
        },
        "password_reset": {
            "customer_name": "John Doe",
            "reset_link": "https://example.com/reset?token=abc123",
            "expiry_hours": "1",
        },
        "team_invite": {
            "invitee_name": "Jane",
            "inviter_name": "John",
            "store_name": "Acme Corp",
            "role": "Admin",
            "accept_url": "https://example.com/accept",
            "expires_in_days": "7",
        },
    }
    return samples.get(template_code, {})
