99 lines
3.4 KiB
Python
99 lines
3.4 KiB
Python
|
|
from __future__ import annotations
|
||
|
|
|
||
|
|
import logging
|
||
|
|
|
||
|
|
from yuxi.channel.extensions.zalouser.errors import (
|
||
|
|
ZaloUserAuthError,
|
||
|
|
ZaloUserConnectionError,
|
||
|
|
)
|
||
|
|
from yuxi.channel.extensions.zalouser.sidecar_client import ZcaSidecarClient
|
||
|
|
|
||
|
|
logger = logging.getLogger(__name__)
|
||
|
|
|
||
|
|
|
||
|
|
class ZaloUserAuthAdapter:
|
||
|
|
def __init__(self):
|
||
|
|
self._client: ZcaSidecarClient | None = None
|
||
|
|
|
||
|
|
def set_client(self, client: ZcaSidecarClient) -> None:
|
||
|
|
self._client = client
|
||
|
|
|
||
|
|
async def login_with_qr_start(
|
||
|
|
self,
|
||
|
|
account_id: str | None = None,
|
||
|
|
*,
|
||
|
|
force: bool = False,
|
||
|
|
timeout_ms: int | None = None,
|
||
|
|
) -> dict:
|
||
|
|
if not self._client:
|
||
|
|
raise ZaloUserAuthError("Sidecar client not initialized")
|
||
|
|
|
||
|
|
timeout = timeout_ms or 30_000
|
||
|
|
try:
|
||
|
|
result = await self._client.login_qr_start(force=force, timeout_ms=timeout)
|
||
|
|
return {
|
||
|
|
"qr_data_url": result.get("qrDataUrl", ""),
|
||
|
|
"message": result.get("message", "QR code generated"),
|
||
|
|
"connected": result.get("connected", False),
|
||
|
|
}
|
||
|
|
except ZaloUserConnectionError as e:
|
||
|
|
return {"qr_data_url": "", "message": str(e), "connected": False}
|
||
|
|
|
||
|
|
async def login_with_qr_wait(
|
||
|
|
self,
|
||
|
|
account_id: str | None = None,
|
||
|
|
*,
|
||
|
|
timeout_ms: int | None = None,
|
||
|
|
current_qr_data_url: str | None = None,
|
||
|
|
) -> dict:
|
||
|
|
if not self._client:
|
||
|
|
raise ZaloUserAuthError("Sidecar client not initialized")
|
||
|
|
|
||
|
|
timeout = timeout_ms or 120_000
|
||
|
|
try:
|
||
|
|
result = await self._client.login_qr_wait(timeout_ms=timeout)
|
||
|
|
return {
|
||
|
|
"connected": True,
|
||
|
|
"message": "Login successful",
|
||
|
|
"qr_data_url": None,
|
||
|
|
"user_id": result.get("user_id", ""),
|
||
|
|
"display_name": result.get("display_name", ""),
|
||
|
|
}
|
||
|
|
except ZaloUserAuthError as e:
|
||
|
|
return {"connected": False, "message": str(e), "qr_data_url": None}
|
||
|
|
|
||
|
|
async def login_with_qr_cancel(self, account_id: str | None = None) -> dict:
|
||
|
|
if not self._client:
|
||
|
|
raise ZaloUserAuthError("Sidecar client not initialized")
|
||
|
|
|
||
|
|
try:
|
||
|
|
await self._client.login_qr_cancel()
|
||
|
|
return {"cancelled": True}
|
||
|
|
except Exception as e:
|
||
|
|
logger.warning("QR cancel failed: %s", e)
|
||
|
|
return {"cancelled": False, "error": str(e)}
|
||
|
|
|
||
|
|
async def logout_account(self, ctx: object) -> dict:
|
||
|
|
if not self._client:
|
||
|
|
return {"cleared": False, "logged_out": None}
|
||
|
|
|
||
|
|
try:
|
||
|
|
await self._client.logout()
|
||
|
|
return {"cleared": True, "logged_out": True}
|
||
|
|
except Exception as e:
|
||
|
|
logger.warning("Logout failed: %s", e)
|
||
|
|
return {"cleared": False, "logged_out": None}
|
||
|
|
|
||
|
|
async def ensure_session(self, timeout_ms: int = 20_000) -> dict:
|
||
|
|
if not self._client:
|
||
|
|
raise ZaloUserAuthError("Sidecar client not initialized")
|
||
|
|
|
||
|
|
try:
|
||
|
|
return await self._client.ensure_session(timeout_ms=timeout_ms)
|
||
|
|
except ZaloUserConnectionError as e:
|
||
|
|
raise ZaloUserAuthError(f"Session ensure failed: {e}") from e
|
||
|
|
|
||
|
|
async def get_cookie(self) -> dict:
|
||
|
|
if not self._client:
|
||
|
|
raise ZaloUserAuthError("Sidecar client not initialized")
|
||
|
|
return await self._client.get_cookie()
|