|
|
@@ -18,6 +18,8 @@ PASS_ACTION = "ADD_TO_CONTENT_POOL"
|
|
|
# 抖音拉作者画像(适老性)的门:只看 query 相关性,不看平台分,保证适老性始终进三项加权。
|
|
|
# 值=抖音入池 query 下限(score_thresholds.douyin.pool_query=65);低于此靠 query 就被否,不拉省成本。
|
|
|
PORTRAIT_QUERY_GATE = 65
|
|
|
+# 画像拉取重试次数(总尝试次数):救热点宝瞬时失败/限速。
|
|
|
+PORTRAIT_FETCH_ATTEMPTS = 2
|
|
|
|
|
|
|
|
|
class SearchCallLimiter:
|
|
|
@@ -147,6 +149,7 @@ class _ProgressiveContext:
|
|
|
# M9 修复:作者画像按作者缓存(画像是作者级,同作者结果一致)。避免对首轮大量视频
|
|
|
# 逐条 30s 限速拉画像 → 同作者只拉一次,把调用量从"视频数"降到"作者数"。None=该作者拉取失败。
|
|
|
self._portrait_by_author: dict[str, dict[str, Any] | None] = {}
|
|
|
+ self._portrait_error_by_author: dict[str, str | None] = {}
|
|
|
|
|
|
def process_query(self, query: dict[str, Any]) -> dict[str, list[dict[str, Any]]]:
|
|
|
"""统一搜索单元(前3命中→剩余→翻页≤3页)。
|
|
|
@@ -377,16 +380,26 @@ class _ProgressiveContext:
|
|
|
author_id = str(author_id)
|
|
|
if author_id in self._portrait_by_author:
|
|
|
portrait = self._portrait_by_author[author_id] # 命中缓存,不再 30s 限速
|
|
|
+ fetch_error = self._portrait_error_by_author.get(author_id)
|
|
|
else:
|
|
|
- try:
|
|
|
- if self.limiter is not None:
|
|
|
- self.limiter.wait()
|
|
|
- portrait = fetch_portrait(author_id)
|
|
|
- except Exception:
|
|
|
- portrait = None
|
|
|
+ portrait, fetch_error = None, None
|
|
|
+ for attempt in range(PORTRAIT_FETCH_ATTEMPTS): # 重试,救瞬时失败/限速
|
|
|
+ try:
|
|
|
+ if self.limiter is not None:
|
|
|
+ self.limiter.wait()
|
|
|
+ portrait = fetch_portrait(author_id)
|
|
|
+ fetch_error = None
|
|
|
+ break
|
|
|
+ except Exception as exc: # 不再吞掉原因:记下来供技术详情展示
|
|
|
+ fetch_error = f"{type(exc).__name__}: {exc}".strip()[:200]
|
|
|
+ portrait = None
|
|
|
self._portrait_by_author[author_id] = portrait
|
|
|
+ self._portrait_error_by_author[author_id] = fetch_error
|
|
|
if portrait is None:
|
|
|
- bundle["content_audience_50plus"] = {"status": "unavailable"}
|
|
|
+ bundle["content_audience_50plus"] = {
|
|
|
+ "status": "unavailable",
|
|
|
+ "failure_reason": fetch_error or "热点宝画像接口未返回数据",
|
|
|
+ }
|
|
|
continue
|
|
|
fans_age = _get_path(portrait, "fans.age.data")
|
|
|
result = fifty_plus_score(fans_age)
|