from pydantic import BaseModel, Field class IdentityInfo(BaseModel): """账号绑定的一端口身份摘要(登录/选择身份时返回)。""" id: str port: str = "opc" role: str = "opc_member" sub_role: str | None = None name: str = "" org_id: str | None = None region_id: str | None = None org_name: str | None = None region_name: str | None = None status: str = "active" class LoginRequest(BaseModel): username: str password: str expires_in: int | None = Field( default=None, description="令牌有效期(秒),-1/0 表示永久,省略为 7 天", ) class RegisterRequest(BaseModel): username: str password: str expires_in: int | None = Field( default=None, description="令牌有效期(秒),-1/0 表示永久,省略为 7 天", ) class UpdateProfileRequest(BaseModel): """更新资料/凭据。``current_password`` 仅在修改用户名/密码时校验。""" current_password: str = "" new_username: str | None = None new_password: str | None = None expires_in: int | None = None # 演示用户资料字段(账户管理页可编辑) nickname: str | None = None # 小程序契约字段(name→nickname;status→opc_status;topics→JSON 列表) name: str | None = None status: str | None = None topics: list[str] | None = None account: str | None = None company: str | None = None room: str | None = None avatar: str | None = None company_avatar: str | None = None class RevokeTokenRequest(BaseModel): token: str | None = Field( default=None, description="要吊销的令牌;省略则吊销当前令牌", ) class AuthStatusResponse(BaseModel): enabled: bool has_users: bool login_modes: list[str] = ["password", "phone"] # password/phone/wechat/miniprogram(四种) wechat_login: bool = False # 小程序扫码(code2session) wx_qr: bool = False # 微信开放平台扫码(OAuth) env: str = "prod" # prod | dev —— 运行环境(前端/联调可据此确认) wxacode_env: str = "release" # release | trial | develop —— 小程序码指向的版本(体验版=trial) class VerifyResponse(BaseModel): valid: bool username: str = "" class UserProfile(BaseModel): """用户资料(登录/me/update-profile 均返回该结构)。""" username: str = "" nickname: str = "" name: str = "" # 别名 = nickname(小程序契约:显示名 / 报名资料姓名) phone: str = "" # 已绑定手机号 phoneBound: bool = False # 是否已绑手机(小程序「已绑定手机」徽标/绑定门槛) wxBound: bool = False # 是否已绑定微信开放平台 openid wxMiniBound: bool = False # 是否已绑定小程序 openid(各端口共享) account: str = "" company: str = "" room: str = "" avatar: str = "" company_avatar: str = "" # RBAC(登录/me 返回;update-profile 不重签时不返回权限明细) role: str = "opc_member" sub_role: str | None = None # 账号类型(四种)与中文标签 —— 前端直接渲染文本,不做代码映射 account_type: str = "service" account_type_label: str = "服务方" org_id: str | None = None region_id: str | None = None permissions: list[str] = Field(default_factory=list) scope_region_ids: list[str] = Field(default_factory=list) # 当前生效的端口身份(多身份绑定) identity_id: str | None = None port: str | None = None identity_name: str = "" class LoginResponse(UserProfile): """登录/注册成功后的响应:资料 + 新令牌。""" token: str = "" identities: list[IdentityInfo] = Field(default_factory=list) class ProfileResponse(UserProfile): """update-profile 成功后的响应;修改凭据时附带新令牌。""" token: str = "" identities: list[IdentityInfo] = Field(default_factory=list) # --------------------------------------------------------------------------- # 统一登录(手机验证码 / 微信)—— 六端登录归一 # --------------------------------------------------------------------------- class SendCodeRequest(BaseModel): phone: str = Field(description="11 位手机号(作为登录账号)") class SendCodeResponse(BaseModel): sent: bool = True message: str = "验证码已发送" # 非空时表示走 stub 直发(仅开发/联调可见) stub_code: str | None = None class PhoneLoginRequest(BaseModel): phone: str code: str = Field(description="手机号接收到的 6 位验证码") class WxLoginRequest(BaseModel): code: str = Field(description="wx.login 返回的 code(未配置 appid 时当作 openid 直通)") nickName: str = "" avatarUrl: str = "" class WxPhoneRequest(BaseModel): openid: str phone: str = Field(description="待补绑的手机号") code: str = Field(description="手机号接收到的验证码") class MpQrConfirmRequest(BaseModel): """小程序扫码登录确认(小程序内 wx.login 后调用)。""" scene: str = Field(description="web/桌面端 /auth/mp-qr/start 返回的场景") code: str = Field(description="wx.login 返回的 code") class BindPhoneRequest(BaseModel): """当前账号绑定手机号(验证码;若该手机号已被其它账号占用则按手机号合并)。""" phone: str code: str = Field(description="发送到该手机号的验证码") class UnbindRequest(BaseModel): """解除已绑定的登录方式(保留至少一种登录方式)。""" type: str = Field(description="phone | wx | wx_mini") # RBAC 管理请求/响应