102 lines
3.9 KiB
Python
102 lines
3.9 KiB
Python
#!/usr/bin/env python3
|
|
"""Re-verify the 32 old VolcanoArk channels directly, delete, and recreate
|
|
live ones with correct type=8 full-path config (PAYGO/CODING/AGENT separated)."""
|
|
import sys, json, time, re
|
|
from pathlib import Path
|
|
from concurrent.futures import ThreadPoolExecutor, as_completed
|
|
sys.path.insert(0, str(Path(__file__).resolve().parent))
|
|
import newapi_client as n
|
|
import importlib.util
|
|
spec = importlib.util.spec_from_file_location(
|
|
"r", str(Path(__file__).resolve().parent / "reconcile_newapi.py"))
|
|
R = importlib.util.module_from_spec(spec); spec.loader.exec_module(R)
|
|
|
|
chans = {c["id"]: c for c in json.load(open("/tmp/chans.json"))}
|
|
volc = [c for c in chans.values() if "VolcanoArk_" in c.get("name", "")
|
|
and "CodingPlan" not in c["name"]]
|
|
all_keys = R.load_all_keys()
|
|
|
|
def findkey(name):
|
|
suf = name.rsplit("_", 1)[-1].lower()
|
|
for k in all_keys:
|
|
if k["prov"] == "volcanoark" and (k["key"].lower()[-4:] == suf
|
|
or k["key"].lower()[-6:].endswith(suf)):
|
|
return k["key"]
|
|
return None
|
|
|
|
def mkch(name, ctype, base, key, models, test_model):
|
|
return dict(name=name, type=ctype, key=key, base_url=base, models=models,
|
|
test_model=test_model, model_mapping="", groups=["default"], group="default",
|
|
priority=0, weight=0, auto_ban=1)
|
|
|
|
print(f"re-verifying {len(volc)} old VolcanoArk channels direct...")
|
|
def work(c):
|
|
key = findkey(c["name"])
|
|
if not key:
|
|
return c["id"], c["name"], None, "NO_KEY"
|
|
v, detail, info = R.verify_volcano(key)
|
|
return c["id"], c["name"], key, (v, detail, info)
|
|
|
|
results = []
|
|
with ThreadPoolExecutor(max_workers=12) as ex:
|
|
futs = [ex.submit(work, c) for c in volc]
|
|
for f in as_completed(futs):
|
|
results.append(f.result())
|
|
if len(results) % 10 == 0:
|
|
print(f" {len(results)}/{len(volc)}")
|
|
|
|
live, dead, other = [], [], []
|
|
for cid, name, key, res in results:
|
|
if key is None:
|
|
other.append((cid, name, res)); continue
|
|
v, detail, info = res
|
|
if v == "USABLE":
|
|
live.append((cid, name, key, info, detail))
|
|
elif v == "DEAD":
|
|
dead.append((cid, name, detail))
|
|
else:
|
|
other.append((cid, name, detail))
|
|
|
|
print(f"\nUSABLE={len(live)} DEAD={len(dead)} OTHER={len(other)}")
|
|
for cid, name, key, info, detail in live:
|
|
print(f" + {cid} {name}: coding={info.get('coding')} agent={info.get('agent')} paygo={info.get('paygo')}")
|
|
for cid, name, d in dead:
|
|
print(f" x DEAD {cid} {name}: {d[:60]}")
|
|
for cid, name, d in other:
|
|
print(f" ? {cid} {name}: {str(d)[:60]}")
|
|
|
|
# delete all old, recreate live
|
|
print("\nrecreating live channels...")
|
|
created = 0
|
|
for cid, name, key, info, detail in live:
|
|
n.delete_channel(cid); time.sleep(0.15)
|
|
suf = name.rsplit("_", 1)[-1]
|
|
newids = []
|
|
if info.get("coding"):
|
|
ch = mkch(f"VolcanoCoding_{suf}", n.TYPE_ANTHROPIC,
|
|
"https://ark.cn-beijing.volces.com/api/coding", key,
|
|
"ark-code-latest", "ark-code-latest")
|
|
ok, msg = n.add_channel(ch)
|
|
if ok: created += 1; print(f" VolcanoCoding_{suf} OK")
|
|
if info.get("agent"):
|
|
ch = mkch(f"VolcanoAgent_{suf}", n.TYPE_CUSTOM,
|
|
"https://ark.cn-beijing.volces.com/api/plan/v3/chat/completions", key,
|
|
"ark-code-latest", "ark-code-latest")
|
|
ok, msg = n.add_channel(ch)
|
|
if ok: created += 1; print(f" VolcanoAgent_{suf} OK")
|
|
for model in info.get("paygo", []):
|
|
tag = model.split("-")[-1][:6]
|
|
ch = mkch(f"VolcanoPAYGO_{suf}_{tag}", n.TYPE_CUSTOM,
|
|
"https://ark.cn-beijing.volces.com/api/v3/chat/completions", key,
|
|
model, model)
|
|
ok, msg = n.add_channel(ch)
|
|
if ok: created += 1; print(f" VolcanoPAYGO_{suf}_{tag} ({model}) OK")
|
|
time.sleep(0.2)
|
|
|
|
# delete dead too
|
|
for cid, name, d in dead:
|
|
n.delete_channel(cid); print(f" deleted dead {cid} {name}")
|
|
time.sleep(0.1)
|
|
|
|
print(f"\n=== created {created} channels from {len(live)} live keys, removed {len(dead)} dead ===")
|