fix(qwen): patch regional dashscope endpoints + inline validator
Qwen patcher had two issues: 1. Only patched dashscope.aliyuncs.com but missed regional endpoints (cn-hongkong, dashscope-intl, dashscope-us). Users in those regions would still hit Aliyun directly. 2. --validate raised ModuleNotFoundError (referenced removed updater/ package). Replaced with self-contained inline checker — 13 GREEN targets covering cli.js markers, settings.json, env vars. Also bump Codex version to v0.122.0 across all READMEs (was v0.116.0). Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
@@ -158,11 +158,19 @@ def patch_cli_js(cli_js_path, config):
|
||||
content, n = re.subn(pat3, rep3, content)
|
||||
results["telemetry_init_guard"] = f"OK ({n})" if n > 0 else "SKIP"
|
||||
|
||||
# Target 4: DASHSCOPE_BASE_URL
|
||||
pat4 = r'(DEFAULT_DASHSCOPE_BASE_URL\s*=\s*)"https://dashscope\.aliyuncs\.com/compatible-mode/v1"'
|
||||
rep4 = rf'\1"{base_url}/v1"'
|
||||
content, n = re.subn(pat4, rep4, content)
|
||||
results["dashscope_base_url"] = f"OK ({n})" if n > 0 else "SKIP"
|
||||
# Target 4: DASHSCOPE_BASE_URL — main + regional (HK/intl/us) endpoints
|
||||
count4 = 0
|
||||
for old_url in [
|
||||
"https://dashscope.aliyuncs.com/compatible-mode/v1",
|
||||
"https://cn-hongkong.dashscope.aliyuncs.com/compatible-mode/v1",
|
||||
"https://dashscope-intl.aliyuncs.com/compatible-mode/v1",
|
||||
"https://dashscope-us.aliyuncs.com/compatible-mode/v1",
|
||||
]:
|
||||
new_url = f"{base_url}/v1"
|
||||
c = content.count(old_url)
|
||||
content = content.replace(old_url, new_url)
|
||||
count4 += c
|
||||
results["dashscope_base_url"] = f"OK ({count4})" if count4 > 0 else "SKIP"
|
||||
|
||||
# Target 5: CODING_PLAN_URLS (string replace, not regex)
|
||||
count5 = 0
|
||||
@@ -403,15 +411,112 @@ def rollback(cli_js_path):
|
||||
# ─── Validation (standalone) ───────────────────────────────────────────
|
||||
|
||||
def run_validation(cli_js_path):
|
||||
"""Run pattern validation on detected installation."""
|
||||
from updater.pattern_validator import validate_all, print_validation_report, get_summary
|
||||
"""Lightweight validation — checks patch markers and key invariants in
|
||||
cli.js + ~/.qwen/settings.json + trustedFolders.json."""
|
||||
counts = {"green": 0, "yellow": 0, "red": 0}
|
||||
print()
|
||||
print(f" {BOLD}Validating Qwen patches{RESET}")
|
||||
print(f" {'─' * 56}")
|
||||
|
||||
user_settings = str(Path.home() / ".qwen" / "settings.json")
|
||||
trusted_folders = str(Path.home() / ".qwen" / "trustedFolders.json")
|
||||
def report(name, status, detail=""):
|
||||
if status == "GREEN":
|
||||
counts["green"] += 1
|
||||
color = GREEN
|
||||
elif status == "YELLOW":
|
||||
counts["yellow"] += 1
|
||||
color = YELLOW
|
||||
else:
|
||||
counts["red"] += 1
|
||||
color = RED
|
||||
suffix = f" — {detail}" if detail else ""
|
||||
print(f" {color}[{status}]{RESET} {name}{suffix}")
|
||||
|
||||
results = validate_all(cli_js_path, user_settings, trusted_folders)
|
||||
counts = print_validation_report(results)
|
||||
return counts, get_summary(results)
|
||||
# cli.js checks
|
||||
if cli_js_path and os.path.isfile(cli_js_path):
|
||||
with open(cli_js_path, "r", encoding="utf-8", errors="replace") as f:
|
||||
content = f.read()
|
||||
|
||||
report("cli.js patch_marker",
|
||||
"GREEN" if PATCH_MARKER in content else "RED",
|
||||
"" if PATCH_MARKER in content else "marker not found")
|
||||
|
||||
report("telemetry_flag",
|
||||
"GREEN" if "getTelemetryEnabled() { return false" in content else "YELLOW")
|
||||
|
||||
report("telemetry_log_prompts",
|
||||
"GREEN" if "getTelemetryLogPromptsEnabled() { return false" in content else "YELLOW")
|
||||
|
||||
# dashscope_base_url: any /compatible-mode/v1 endpoint left = RED
|
||||
leftover_ds = [u for u in [
|
||||
"dashscope.aliyuncs.com/compatible-mode",
|
||||
"cn-hongkong.dashscope.aliyuncs.com/compatible-mode",
|
||||
"dashscope-intl.aliyuncs.com/compatible-mode",
|
||||
"dashscope-us.aliyuncs.com/compatible-mode",
|
||||
] if u in content]
|
||||
report("dashscope_base_url",
|
||||
"GREEN" if not leftover_ds else "RED",
|
||||
f"unpatched: {', '.join(leftover_ds)}" if leftover_ds else "")
|
||||
|
||||
leftover_cp = [u for u in [
|
||||
"coding.dashscope.aliyuncs.com",
|
||||
"coding-intl.dashscope.aliyuncs.com",
|
||||
] if u in content]
|
||||
report("coding_plan_urls",
|
||||
"GREEN" if not leftover_cp else "RED",
|
||||
f"unpatched: {', '.join(leftover_cp)}" if leftover_cp else "")
|
||||
|
||||
report("default_model",
|
||||
"GREEN" if 'DEFAULT_QWEN_MODEL = "coder-model"' in content else "YELLOW")
|
||||
|
||||
report("mainline_model",
|
||||
"GREEN" if 'MAINLINE_CODER_MODEL = "qwen3.5-plus"' in content else "YELLOW")
|
||||
|
||||
report("auto_update_registry",
|
||||
"GREEN" if '"https://registry.npmjs.org/"' not in content else "YELLOW")
|
||||
else:
|
||||
report("cli.js", "RED", f"not found: {cli_js_path}")
|
||||
|
||||
# settings.json checks
|
||||
settings_path = Path.home() / ".qwen" / "settings.json"
|
||||
if settings_path.is_file():
|
||||
try:
|
||||
with open(settings_path, "r", encoding="utf-8") as f:
|
||||
settings = json.load(f)
|
||||
sec = settings.get("security", {})
|
||||
auth = sec.get("auth", {})
|
||||
telemetry = settings.get("telemetry", {})
|
||||
report("user_settings.auth.selectedType",
|
||||
"GREEN" if auth.get("selectedType") == "openai" else "YELLOW",
|
||||
f"value={auth.get('selectedType')!r}")
|
||||
report("user_settings.telemetry.enabled",
|
||||
"GREEN" if telemetry.get("enabled") is False else "YELLOW")
|
||||
except Exception as e:
|
||||
report("user_settings", "RED", f"parse error: {e}")
|
||||
else:
|
||||
report("user_settings", "YELLOW", f"missing: {settings_path}")
|
||||
|
||||
# trustedFolders.json checks
|
||||
trusted_path = Path.home() / ".qwen" / "trustedFolders.json"
|
||||
if trusted_path.is_file():
|
||||
report("trusted_folders", "GREEN", "present")
|
||||
else:
|
||||
report("trusted_folders", "YELLOW", "missing")
|
||||
|
||||
# env vars
|
||||
has_api = bool(os.environ.get("OPENAI_API_KEY"))
|
||||
has_url = bool(os.environ.get("OPENAI_BASE_URL"))
|
||||
report("env.OPENAI_API_KEY",
|
||||
"GREEN" if has_api else "YELLOW",
|
||||
"" if has_api else "not set in current shell")
|
||||
report("env.OPENAI_BASE_URL",
|
||||
"GREEN" if has_url else "YELLOW",
|
||||
"" if has_url else "not set in current shell")
|
||||
|
||||
print(f" {'─' * 56}")
|
||||
print(f" {GREEN}GREEN: {counts['green']}{RESET} "
|
||||
f"{YELLOW}YELLOW: {counts['yellow']}{RESET} "
|
||||
f"{RED}RED: {counts['red']}{RESET}")
|
||||
return counts, f"{counts['green']}G/{counts['yellow']}Y/{counts['red']}R"
|
||||
|
||||
|
||||
# ─── CLI ───────────────────────────────────────────────────────────────
|
||||
|
||||
Reference in New Issue
Block a user