Files
HyperNode-AI/app/jobs/daily_yield.py
T
dekun 2bbdb00a4d 初始化 HyperNode-AI 控制面。
包含节点账本、每日清算,以及 Ubuntu 交互式部署脚本。

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-10-10 21:53:20 +08:00

42 lines
1.5 KiB
Python

"""每天凌晨的积分清算任务。"""
from __future__ import annotations
import logging
from datetime import date, datetime, timedelta, timezone
from app.clock import utcnow
from app.database import session_scope
from app.services.heartbeat import mark_stale_nodes
from app.services.yield_engine import SettleSummary, settle_yield_date
logger = logging.getLogger(__name__)
def run_daily_yield_cron(now: datetime | None = None, yield_date: date | None = None) -> SettleSummary:
"""计算所有仍在授权期内的节点,并把当日积分写入 node_yields。
调度器在北京时间 00:05 调用本函数。账本按 UTC 日切分,因此入账日期是
调用时刻之前最近一个已经结束的 UTC 日,而不是刚开始的这一天。
同一节点同一天已有流水时跳过,重复触发不会重复入账。
"""
moment = now or utcnow()
if moment.tzinfo is None:
raise ValueError("清算时间必须带时区")
target = yield_date or (moment.astimezone(timezone.utc).date() - timedelta(days=1))
with session_scope() as session:
stale = mark_stale_nodes(session, moment)
summary = settle_yield_date(session, target, moment)
logger.info(
"daily yield settled date=%s created=%s skipped=%s points=%s partial=%s stale_nodes=%s",
summary.yield_date,
summary.created,
summary.skipped,
format(summary.total_points, "f"),
summary.is_partial,
len(stale),
)
return summary