Files
banban/mini-program/app/service/parent.py

103 lines
3.1 KiB
Python

from collections.abc import Mapping
from typing import Optional
from app.dao.parent import ParentDAO
from app.service.avatar_storage import AvatarStorageService
from app.settings import settings
class ParentService:
def __init__(self, db, avatar_storage: AvatarStorageService | None = None):
self.dao = ParentDAO(db)
self.avatar_storage = avatar_storage or AvatarStorageService()
def create(
self,
openid: str,
unionid: Optional[str] = None,
nickname: Optional[str] = None,
avatar_url: Optional[str] = None,
) -> Mapping:
user_id = self.dao.upsert(openid, unionid, nickname, avatar_url)
return self.get(user_id)
def get(self, user_id: int) -> Optional[Mapping]:
return self._present_parent(self.dao.get_by_id(user_id))
def update(
self,
user_id: int,
nickname: Optional[str] = None,
avatar_url: Optional[str] = None,
phone: Optional[str] = None,
) -> Mapping:
self.dao.update(user_id, nickname, avatar_url, phone)
return self.get(user_id)
def upload_avatar(
self,
*,
user_id: int,
filename: str | None,
content_type: str | None,
content: bytes,
) -> Optional[Mapping]:
existing = self.dao.get_by_id(user_id)
if not existing:
return None
stored = self.avatar_storage.upload_avatar(
user_id=user_id,
filename=filename,
content_type=content_type,
content=content,
)
old_avatar_file_key = existing.get("avatar_file_key")
try:
self.dao.set_avatar_file_key(user_id, stored.file_key)
except Exception:
try:
self.avatar_storage.delete_avatar(stored.file_key)
except Exception:
pass
raise
if old_avatar_file_key and old_avatar_file_key != stored.file_key:
try:
self.avatar_storage.delete_avatar(old_avatar_file_key)
except Exception:
pass
return self.get(user_id)
def get_avatar_download(self, user_id: int) -> Optional[dict]:
parent = self.dao.get_by_id(user_id)
if not parent:
return None
avatar_file_key = parent.get("avatar_file_key")
if avatar_file_key:
return {
"avatar_url": self.avatar_storage.get_avatar_url(avatar_file_key),
"expires_in": settings.cos_avatar_url_expire_seconds,
}
avatar_url = parent.get("avatar_url")
if avatar_url:
return {
"avatar_url": avatar_url,
"expires_in": None,
}
return None
def _present_parent(self, parent: Optional[Mapping]) -> Optional[dict]:
if not parent:
return None
data = dict(parent)
avatar_file_key = data.get("avatar_file_key")
if avatar_file_key:
data["avatar_url"] = self.avatar_storage.get_avatar_url(avatar_file_key)
return data