瀏覽代碼

feat(plugin): 0.8.1 —— 加入 staging 站点,且明确它是另一个库

staging.wikipali.org 加进内置站点清单。关键是它**不能进 online 桶**——三条实测
判据都指向它是独立数据库:

  站点      公开 channel   _System_commentary_ 的 uid   ai-model-token
  www/next     561         083a4dfa-5253…               404(无此路由)
  staging      559         bda6b9a2-505b…               405(路由已存在)

同名 channel 的 uid 不同就是不同的库。若按老逻辑(除 local 外都算线上)加进去,
后果是凭据混用、以及**自动 fallback 把线上查询静默甩到 staging**——正是设计上
一直在防的「查到的数据不是你以为的那个库」。

所以 SITES 加了显式的 bucket 字段,不再用「不是 local 就是线上」推断:
online 四个共享库与密钥、彼此可 fallback;staging 与 local 各自一桶、不参与
fallback。bucket_name_for 改为查表。切到非 online 桶时的提示也改写为「该地址是
**另一个数据库**」,原来只说「不共用数据库/密钥」,份量不够。

顺带一个发现:staging 的 ai-model-token 返回 405,说明写入端那批 P0 代码已经
部署在 staging 上了——线上四站还都是 404。写端的线上复测因此有了可跑的环境。

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
visuddhinanda 1 周之前
父節點
當前提交
e8c2770f04

+ 1 - 1
plugins/wikipali/.claude-plugin/plugin.json

@@ -1,7 +1,7 @@
 {
   "name": "wikipali",
   "description": "WikiPali 巴利三藏平台的客户端:检索与阅读语料做研究(词形展开、全文检索、出处分布、按坐标取原文与译本),以及以 AI 模型身份写入句子。",
-  "version": "0.8.0",
+  "version": "0.8.1",
   "author": {
     "name": "visuddhinanda",
     "url": "https://github.com/visuddhinanda"

+ 4 - 2
plugins/wikipali/lib/cmd_site.py

@@ -22,7 +22,8 @@ def cmd_endpoint(args):
             note(f"注意:当前地址来自 {src},是一次性覆盖,未写入凭据文件。")
         if current_url not in [s["url"] for s in SITES]:
             print(f"  *) {current_url:<32} 自定义地址  ← 当前")
-        print("\n切换:wikipali endpoint <序号|www|www.cc|next|next.cc|local|完整url>")
+        keys = "|".join(x["key"] for x in SITES)
+        print(f"\n切换:wikipali endpoint <序号|{keys}|完整url>")
         return 0
 
     url = normalize_api_url(expand_site_alias(args.target))
@@ -33,7 +34,8 @@ def cmd_endpoint(args):
     save_creds(creds)
     print(f"已切换到 {url}({site_label(url)})")
     if name != "online":
-        note("提示:该地址与线上四站不共用数据库/密钥,凭据是独立的一桶,可能需要重新登录。")
+        note("提示:该地址是**另一个数据库**,与线上四站不共用数据与密钥。"
+             "凭据和本地缓存都是独立的一桶,可能需要在该站点重新登录。")
     return 0
 
 

+ 10 - 6
plugins/wikipali/lib/creds.py

@@ -8,7 +8,7 @@ import os
 import stat
 
 from errors import WpError
-from sites import DEFAULT_API_URL, LOCAL_URL, ONLINE_URLS, expand_site_alias, normalize_api_url
+from sites import BUCKET_BY_URL, DEFAULT_API_URL, LOCAL_URL, expand_site_alias, normalize_api_url
 
 
 CREDS_DIR = os.path.join(os.path.expanduser("~"), ".wikipali")
@@ -46,11 +46,15 @@ def save_creds(creds):
 
 
 def bucket_name_for(api_url):
-    """凭据桶名。线上四地址共用 online 桶;开发机 local;其余地址自成一桶。"""
-    if api_url in ONLINE_URLS:
-        return "online"
-    if api_url == LOCAL_URL:
-        return "local"
+    """凭据(与本地缓存)的桶名。
+
+    只有线上四个地址共享同一个库与密钥,共用 online 桶;staging、开发机、以及任何
+    自定义地址都是**另一个库**,各自一桶——混用会让凭据失效,更糟的是让查询静默
+    落到错误的数据上。
+    """
+    known = BUCKET_BY_URL.get(api_url)
+    if known:
+        return known
     return "site:" + api_url
 
 

+ 19 - 7
plugins/wikipali/lib/sites.py

@@ -10,16 +10,28 @@ import urllib.parse
 from errors import WpError
 
 
+# bucket 决定两件事:凭据/缓存存哪一桶,以及能不能作为自动 fallback 的目标。
+# 只有 bucket == "online" 的四个地址共享同一个数据库与 jwt 密钥,彼此可以互替。
+# staging 与开发机各是**另一个库**——实测 staging 的公开 channel 数与线上不同,
+# 同名 channel 的 uid 也不同——所以自成一桶,且绝不参与 fallback。
 SITES = [
-    {"key": "www", "url": "https://www.wikipali.org/api", "version": "稳定版", "domain": ".org"},
-    {"key": "www.cc", "url": "https://www.wikipali.cc/api", "version": "稳定版", "domain": ".cc"},
-    {"key": "next", "url": "https://next.wikipali.org/api", "version": "最新版", "domain": ".org"},
-    {"key": "next.cc", "url": "https://next.wikipali.cc/api", "version": "最新版", "domain": ".cc"},
-    {"key": "local", "url": "http://127.0.0.1:8000/api", "version": "开发机", "domain": "本机"},
+    {"key": "www", "url": "https://www.wikipali.org/api",
+     "version": "稳定版", "domain": ".org", "bucket": "online"},
+    {"key": "www.cc", "url": "https://www.wikipali.cc/api",
+     "version": "稳定版", "domain": ".cc", "bucket": "online"},
+    {"key": "next", "url": "https://next.wikipali.org/api",
+     "version": "最新版", "domain": ".org", "bucket": "online"},
+    {"key": "next.cc", "url": "https://next.wikipali.cc/api",
+     "version": "最新版", "domain": ".cc", "bucket": "online"},
+    {"key": "staging", "url": "https://staging.wikipali.org/api",
+     "version": "预发布", "domain": "独立库", "bucket": "staging"},
+    {"key": "local", "url": "http://127.0.0.1:8000/api",
+     "version": "开发机", "domain": "独立库", "bucket": "local"},
 ]
 
-ONLINE_URLS = [s["url"] for s in SITES if s["key"] != "local"]
-LOCAL_URL = SITES[-1]["url"]
+ONLINE_URLS = [s["url"] for s in SITES if s["bucket"] == "online"]
+LOCAL_URL = next(s["url"] for s in SITES if s["key"] == "local")
+BUCKET_BY_URL = {s["url"]: s["bucket"] for s in SITES}
 DEFAULT_API_URL = SITES[0]["url"]
 
 

+ 5 - 1
plugins/wikipali/references/conventions.md

@@ -74,7 +74,11 @@ AI-汉译-Nissaya(**AI 生成**,deepseek-v3)(216:35)         ← 机器译
 
 ## 站点
 
-线上四个地址(`www`/`next` × `.org`/`.cc`)共享同一个数据库和密钥,凭据通用。
+**线上四个地址**(`www`/`next` × `.org`/`.cc`)共享同一个数据库和密钥,凭据通用。
+**`staging` 与开发机 `local` 是另外的数据库**,各自一桶——实测 staging 的公开 channel
+数与线上不同(559 vs 561),同名 channel 的 uid 也不同,**在 staging 上查到的坐标不能
+直接拿到线上引用**。自动 fallback 只在线上四站之间发生,绝不会落到这两个上。
+
 `www` 是稳定版、`next` 是最新版**代码**,不是不同的数据环境。较新的端点在稳定版上
 返回 404,意思是"该站点代码版本还没到",不是"资源不存在"。