"""cps_wx_user 数据访问:按 openid upsert。"""
from __future__ import annotations

from sqlalchemy import func, select
from sqlalchemy.orm import Session

from app.models.cps_wx_user import CpsWxUser


def get_by_openid(db: Session, openid: str) -> CpsWxUser | None:
    return db.execute(
        select(CpsWxUser).where(CpsWxUser.openid == openid)
    ).scalar_one_or_none()


def upsert(
    db: Session, *, openid: str, code: str | None = None, group_id: int | None = None,
    nickname: str | None = None, headimgurl: str | None = None, unionid: str | None = None,
) -> CpsWxUser:
    """按 openid upsert。

    - 首次:建行,记来源 code/group。
    - 已存在:仅在传入非 None 时更新昵称/头像/unionid(base 阶段为 None,不覆盖已有画像);
      并刷新 last_seen(显式 set,因 onupdate 仅在字段有变更时触发)。
    """
    u = get_by_openid(db, openid)
    if u is None:
        u = CpsWxUser(
            openid=openid, first_code=code, first_group_id=group_id,
            nickname=nickname, headimgurl=headimgurl, unionid=unionid,
        )
        db.add(u)
    else:
        if nickname is not None:
            u.nickname = nickname
        if headimgurl is not None:
            u.headimgurl = headimgurl
        if unionid is not None:
            u.unionid = unionid
        u.last_seen = func.now()
    db.commit()
    db.refresh(u)
    return u
