60 lines
3.1 KiB
Python
60 lines
3.1 KiB
Python
import os, paramiko, json
|
|
PW = os.environ["REMOTE_PASS"]
|
|
c = paramiko.SSHClient()
|
|
c.set_missing_host_key_policy(paramiko.AutoAddPolicy())
|
|
c.connect("207.57.129.228", port=19717, username="root", password=PW, timeout=15, allow_agent=False, look_for_keys=False)
|
|
def run(cmd, t=120):
|
|
si, so, se = c.exec_command(cmd, timeout=t)
|
|
out = so.read().decode("utf-8", "replace")
|
|
err = se.read().decode("utf-8", "replace")
|
|
rc = so.channel.recv_exit_status()
|
|
if out: print(out, end="")
|
|
if err: print("[err]", err, end="", file=__import__("sys").stderr)
|
|
return out
|
|
|
|
# 1) 找带错误信息的文章(翻译状态虽然 ok 但字段里带"翻译失败"字样)
|
|
print("--- 找出还残留错误标记的文章 ---")
|
|
n = run("docker exec news-aggregator-postgres-1 psql -U news -d news -tA -c \"SELECT count(*) FROM articles WHERE title_zh LIKE '%[翻译失败:%' OR body_zh_text LIKE '%[翻译失败:%';\"")
|
|
print(f" 残留错误文章数: {n.strip()}")
|
|
|
|
# 2) 改回 pending
|
|
print("\n--- 批量回退到 pending ---")
|
|
run("docker exec news-aggregator-postgres-1 psql -U news -d news -c \"UPDATE articles SET translation_status = 'pending', title_zh = NULL, body_zh_text = NULL, body_zh_html = NULL WHERE title_zh LIKE '%[翻译失败:%' OR body_zh_text LIKE '%[翻译失败:%';\" 2>&1 | tail -3")
|
|
|
|
# 3) 触发 worker 翻译
|
|
print("\n--- 触发翻译(120s 等待)---")
|
|
run("cd /srv/news && docker exec news-aggregator-worker-1 python -c 'import asyncio; from app.workers.pipeline import _translate_recent_for_source; async def t(): [await _translate_recent_for_source(sid, max_n=300) for sid in [2,3,4,5]]; asyncio.run(t())' 2>&1 | tail -10", t=180)
|
|
import time
|
|
time.sleep(10)
|
|
|
|
# 4) 翻译后统计
|
|
print("\n--- 翻译后统计 ---")
|
|
run("docker exec news-aggregator-postgres-1 psql -U news -d news -c \"SELECT translation_status, translation_engine, count(*), sum(translation_chars) FROM articles GROUP BY 1, 2 ORDER BY 1, 2;\"")
|
|
|
|
# 5) 看一条 BBC 详情
|
|
print("\n--- BBC 详情 ---")
|
|
out = run("curl -s -X POST http://localhost/api/v1/auth/login -H 'Content-Type: application/json' -d '{\"username\":\"owner\",\"password\":\"Owner2026!\"}'")
|
|
token = json.loads(out)["access_token"]
|
|
out = run(f"curl -s -H 'Authorization: Bearer {token}' 'http://localhost/api/v1/articles?source=bbc-world&limit=1'")
|
|
ad = json.loads(out)
|
|
if ad.get("items"):
|
|
aid = ad["items"][0]["id"]
|
|
out = run(f"curl -s -H 'Authorization: Bearer {token}' 'http://localhost/api/v1/articles/{aid}'")
|
|
try:
|
|
det = json.loads(out)
|
|
print(f"\n=== {det['source']['name']} #{aid} ===")
|
|
print(f" title: {det['title'][:80]}")
|
|
print(f" title_zh: {(det.get('title_zh') or '—')[:80]}")
|
|
print(f" body_text 长度: {len(det['body_text'])}")
|
|
print(f" body_zh_text 长度: {len(det.get('body_zh_text') or '')}")
|
|
if det.get("body_zh_text"):
|
|
print(f"\n 译文(前 600 字符):")
|
|
print(f" {det['body_zh_text'][:600]}")
|
|
except Exception as e:
|
|
print(f" err: {e}\n raw: {out[:200]}")
|
|
|
|
# 6) /me/usage
|
|
u = json.loads(run(f"curl -s -H 'Authorization: Bearer {token}' 'http://localhost/api/v1/me/usage'"))
|
|
print(f"\n--- /me/usage ---\n {u}")
|
|
c.close()
|