"""PWA Web Push 알림 — pywebpush 라이브러리 활용.

환경변수:
  VAPID_PRIVATE_KEY:   VAPID 개인키 (base64url 또는 PEM)
  VAPID_PUBLIC_KEY:    VAPID 공개키 (브라우저 subscribe 시 사용)
  VAPID_CLAIMS_EMAIL:  관리자 이메일 (mailto: claim)
"""
from __future__ import annotations

import json
import logging
import os
from typing import Optional

logger = logging.getLogger(__name__)

VAPID_PRIVATE_KEY = os.getenv("VAPID_PRIVATE_KEY", "")
VAPID_PUBLIC_KEY  = os.getenv("VAPID_PUBLIC_KEY", "")
VAPID_EMAIL       = os.getenv("VAPID_CLAIMS_EMAIL", "admin@guardia.local")


async def send_push(
    subscription_info: dict,
    title: str,
    body: str,
    url: str = "/",
    icon: str = "/static/icons/icon-192.png",
) -> bool:
    """단일 푸시 구독에 알림 전송. 성공 시 True."""
    if not VAPID_PRIVATE_KEY:
        logger.debug("VAPID_PRIVATE_KEY 미설정 — 푸시 알림 스킵")
        return False
    try:
        from pywebpush import webpush, WebPushException
        webpush(
            subscription_info=subscription_info,
            data=json.dumps({
                "title": title,
                "body":  body,
                "url":   url,
                "icon":  icon,
            }),
            vapid_private_key=VAPID_PRIVATE_KEY,
            vapid_claims={"sub": f"mailto:{VAPID_EMAIL}"},
        )
        return True
    except Exception as e:
        logger.warning("푸시 알림 전송 실패: %s", str(e)[:100])
        return False


async def broadcast_push(
    title: str,
    body: str,
    url: str = "/",
    user_ids: Optional[list] = None,
) -> dict:
    """
    여러 사용자에게 Push 브로드캐스트.
    user_ids=None 이면 전체 구독자에게 발송.
    Returns: {"sent": int, "failed": int}
    """
    from database import SessionLocal
    from models import PushSubscription
    from sqlalchemy import select

    sent = 0
    failed = 0

    try:
        async with SessionLocal() as db:
            q = select(PushSubscription)
            if user_ids:
                q = q.where(PushSubscription.user_id.in_(user_ids))
            subs = (await db.execute(q)).scalars().all()

        for sub in subs:
            info = {
                "endpoint": sub.endpoint,
                "keys": {
                    "p256dh": sub.p256dh,
                    "auth":   sub.auth,
                },
            }
            ok = await send_push(info, title, body, url)
            if ok:
                sent += 1
            else:
                failed += 1
    except Exception as e:
        logger.error("브로드캐스트 푸시 오류: %s", e)

    return {"sent": sent, "failed": failed}
