虎牙精英宝典

This commit is contained in:
yml2213
2026-08-31 19:34:59 +08:00
parent d391e2ce3e
commit 955ba45488
16 changed files with 743 additions and 5 deletions
+78
View File
@@ -50,6 +50,8 @@ from ..models import (
HuyaRegisterItem,
HuyaRegisterSuccessLog,
HuyaTask,
HuyaWorkbench,
HuyaWorkbenchAccount,
ProxyConfig,
User,
)
@@ -79,6 +81,7 @@ from ..schemas import (
HuyaSmsLoginRequest,
HuyaTaskBatchRequest,
HuyaTaskOut,
HuyaWorkbenchAccountsUpdate,
)
from ..services.audit_service import record_audit
from ..services.huya_register_runner import (
@@ -281,6 +284,18 @@ def _require_huya_task_account_access(
raise HTTPException(status_code=403, detail="包含无权操作的虎牙账号")
def _elite_workbench_account_ids(db: Session, current: User) -> list[int]:
query = db.query(HuyaWorkbenchAccount.account_id).filter(
HuyaWorkbenchAccount.user_id == current.id,
HuyaWorkbenchAccount.handbook_scope == "elite",
)
if not _can_view_huya_all(current):
query = query.join(HuyaAccount, HuyaAccount.id == HuyaWorkbenchAccount.account_id).filter(
HuyaAccount.assigned_to == current.id
)
return [account_id for (account_id,) in query.order_by(HuyaWorkbenchAccount.id.asc()).all()]
def _require_huya_batch_owner(db: Session, current: User, batch_id: str) -> None:
"""客服只能停止或订阅自己创建的任务批次。"""
if _can_view_huya_all(current):
@@ -385,6 +400,7 @@ def _task_out(task: HuyaTask, *, include_images: bool = False) -> HuyaTaskOut:
account_uid=account.uid if account else "",
account_nickname=account.nickname if account else "",
task_type=task.task_type,
handbook_scope=getattr(task, "handbook_scope", "legacy") or "legacy",
status=task.status or "",
message=task.message or "",
result=_sanitize_task_result(
@@ -1282,6 +1298,9 @@ def delete_accounts_batch(
db.query(HuyaTask).filter(HuyaTask.account_id.in_(ids)).delete(
synchronize_session=False
)
db.query(HuyaWorkbenchAccount).filter(
HuyaWorkbenchAccount.account_id.in_(ids)
).delete(synchronize_session=False)
_clear_huya_account_references(db, ids)
deleted = (
db.query(HuyaAccount)
@@ -1310,6 +1329,9 @@ def delete_accounts_batch_selection(
db.query(HuyaTask).filter(HuyaTask.account_id.in_(ids)).delete(
synchronize_session=False
)
db.query(HuyaWorkbenchAccount).filter(
HuyaWorkbenchAccount.account_id.in_(ids)
).delete(synchronize_session=False)
_clear_huya_account_references(db, ids)
deleted = (
db.query(HuyaAccount)
@@ -1339,6 +1361,9 @@ def delete_account(
db.query(HuyaTask).filter(HuyaTask.account_id == account_id).delete(
synchronize_session=False
)
db.query(HuyaWorkbenchAccount).filter(
HuyaWorkbenchAccount.account_id == account_id
).delete(synchronize_session=False)
_clear_huya_account_references(db, [account_id])
db.delete(account)
db.commit()
@@ -1743,6 +1768,55 @@ def update_config(
return _config_out(config)
@router.get("/workbench-accounts")
def list_huya_workbench_accounts(
handbook_scope: str = Query(..., pattern="^elite$"),
db: Session = Depends(get_db),
current: User = Depends(require_permission("huya:task")),
):
"""读取当前用户的虎牙精英宝典账号集合。"""
ids = _elite_workbench_account_ids(db, current)
configured = db.query(HuyaWorkbench.id).filter(
HuyaWorkbench.user_id == current.id,
HuyaWorkbench.handbook_scope == handbook_scope,
).first() is not None
return {"account_ids": ids, "configured": configured}
@router.put("/workbench-accounts")
def update_huya_workbench_accounts(
req: HuyaWorkbenchAccountsUpdate,
db: Session = Depends(get_db),
current: User = Depends(require_permission("huya:task")),
):
"""覆盖虎牙精英宝典账号集合,支持跨浏览器同步。"""
ids = sorted(set(req.account_ids))
if any(account_id < 1 for account_id in ids):
raise HTTPException(status_code=400, detail="无效的账号 ID")
if ids:
_require_huya_task_account_access(db, current, ids)
workbench = db.query(HuyaWorkbench).filter(
HuyaWorkbench.user_id == current.id,
HuyaWorkbench.handbook_scope == req.handbook_scope,
).first()
if workbench is None:
db.add(HuyaWorkbench(user_id=current.id, handbook_scope=req.handbook_scope))
else:
workbench.updated_at = datetime.now(UTC)
db.query(HuyaWorkbenchAccount).filter(
HuyaWorkbenchAccount.user_id == current.id,
HuyaWorkbenchAccount.handbook_scope == req.handbook_scope,
).delete(synchronize_session=False)
db.add_all([
HuyaWorkbenchAccount(
user_id=current.id, handbook_scope=req.handbook_scope, account_id=account_id
)
for account_id in ids
])
db.commit()
return {"account_ids": ids, "success": True}
@router.get("/goods", response_model=list[HuyaGoodsOut])
def list_goods(
db: Session = Depends(get_db),
@@ -1794,6 +1868,7 @@ async def create_task_batch(
req.task_type,
current.id,
req.payload,
req.handbook_scope,
)
except ValueError as exc:
raise HTTPException(status_code=400, detail=str(exc)) from exc
@@ -1838,6 +1913,7 @@ async def create_task_batch(
@router.get("/tasks", response_model=list[HuyaTaskOut])
def list_tasks(
batch_id: str | None = None,
handbook_scope: str | None = Query(None, pattern="^(legacy|elite)$"),
include_images: bool = Query(
False, description="是否返回 base64 小程序码(默认否,轮询请保持 false)"
),
@@ -1848,6 +1924,8 @@ def list_tasks(
query = _visible_huya_tasks_query(db, current)
if batch_id:
query = query.filter(HuyaTask.batch_id == batch_id)
if handbook_scope:
query = query.filter(HuyaTask.handbook_scope == handbook_scope)
tasks = query.order_by(HuyaTask.id.desc()).limit(300).all()
return [_task_out(task, include_images=include_images) for task in tasks]