"""设备注册 / 心跳 endpoint(无障碍保护存活检测)。

路由前缀 /api/v1/device,需 Bearer 鉴权(设备绑登录用户)。
  POST /register   注册设备 / 更新 registration_id(App 前台、拿到 push token 时调)
  POST /heartbeat  上报心跳(无障碍服务存活时周期调,刷新存活)

后端 heartbeat_monitor_worker 据此发现心跳超时的设备并极光推送告警。
见 spec: spec/accessibility-liveness-push.md。
"""
from __future__ import annotations

import logging

from fastapi import APIRouter

from app.api.deps import CurrentUser, DbSession
from app.repositories import device as device_repo
from app.schemas.device import (
    DeviceOut,
    DeviceRegisterRequest,
    HeartbeatRequest,
    LivenessAckRequest,
    LivenessOut,
    OkResponse,
)

logger = logging.getLogger("shagua.device")

router = APIRouter(prefix="/api/v1/device", tags=["device"])


@router.post("/register", response_model=DeviceOut, summary="注册设备/更新推送token")
def register_device(
    req: DeviceRegisterRequest,
    user: CurrentUser,
    db: DbSession,
) -> DeviceOut:
    device = device_repo.register_or_update(
        db,
        user_id=user.id,
        device_id=req.device_id,
        registration_id=req.registration_id,
        platform=req.platform,
        app_version=req.app_version,
    )
    logger.info(
        "device register user_id=%d device_id=%s reg=%s",
        user.id,
        req.device_id,
        bool(req.registration_id),
    )
    return DeviceOut.model_validate(device)


@router.post("/heartbeat", response_model=OkResponse, summary="上报心跳")
def report_heartbeat(
    req: HeartbeatRequest,
    user: CurrentUser,
    db: DbSession,
) -> OkResponse:
    device_repo.touch_heartbeat(
        db,
        user_id=user.id,
        device_id=req.device_id,
        accessibility_enabled=req.accessibility_enabled,
        registration_id=req.registration_id,
    )
    return OkResponse()


@router.get("/liveness", response_model=LivenessOut, summary="查询本机掉线告警(后置检测)")
def get_liveness(
    device_id: str,
    user: CurrentUser,
    db: DbSession,
) -> LivenessOut:
    """客户端进 App 时拉取: 本机是否被判定掉线过(kill_alert_pending)。

    设备从未注册过 → 返回默认(无告警)。命中 → 客户端弹「开启自启动」引导, 之后调 /liveness/ack 清。
    见 spec: spec/accessibility-liveness-pull-prompt.md。
    """
    device = device_repo.get_device(db, user_id=user.id, device_id=device_id)
    if device is None:
        return LivenessOut()
    return LivenessOut.model_validate(device)


@router.post("/liveness/ack", response_model=OkResponse, summary="确认已提醒(清掉线告警)")
def ack_liveness(
    req: LivenessAckRequest,
    user: CurrentUser,
    db: DbSession,
) -> OkResponse:
    """客户端已弹过「开启自启动」引导 → 清掉「待提醒」标记(下次真掉线 worker 再置)。"""
    device_repo.ack_kill_alert(db, user_id=user.id, device_id=req.device_id)
    return OkResponse()
