#!/usr/bin/env python3 """ 仅应用 JSON 补丁中的配置项,不与 DEFAULT_RECOMMENDED 合并。 用于小幅改库,避免误把 apply_recommended_config 内置批量默认值重新刷一遍。 JSON 格式与 apply_recommended_config.py --from 相同(数组或对象)。 """ from __future__ import annotations import argparse import sys from pathlib import Path PROJECT_ROOT = Path(__file__).resolve().parent.parent SCRIPTS_DIR = PROJECT_ROOT / "scripts" BACKEND_DIR = PROJECT_ROOT / "backend" for p in (SCRIPTS_DIR, BACKEND_DIR, PROJECT_ROOT): if str(p) not in sys.path: sys.path.insert(0, str(p)) from apply_recommended_config import infer_type, load_external_json def main() -> None: parser = argparse.ArgumentParser(description="仅应用补丁 JSON 中的全局策略配置(不合并内置默认)") parser.add_argument("--from", dest="from_path", required=True, help="补丁 JSON 路径") parser.add_argument("--dry-run", action="store_true", help="只打印,不落库") parser.add_argument("--updated-by", default="apply_config_patch_only", help="写入 updated_by") args = parser.parse_args() from_path = Path(args.from_path) if not from_path.is_absolute(): from_path = PROJECT_ROOT / from_path if not from_path.is_file(): raise FileNotFoundError(f"未找到配置文件: {from_path}") patch = load_external_json(from_path) if not patch: print("补丁为空,退出") return print(f"将应用 {len(patch)} 个配置项(仅补丁,dry_run={args.dry_run})") for key in sorted(patch.keys()): meta = patch[key] print(f" - {key} = {meta.get('value')} [{meta.get('type')}/{meta.get('category')}]") if args.dry_run: return from database.models import GlobalStrategyConfig mgr = None try: import config_manager if hasattr(config_manager, "GlobalStrategyConfigManager"): mgr = config_manager.GlobalStrategyConfigManager() except Exception: mgr = None ok, fail = 0, 0 for key, meta in patch.items(): try: GlobalStrategyConfig.set( key, meta.get("value"), meta.get("type") or infer_type(meta.get("value")), meta.get("category") or "strategy", meta.get("description"), updated_by=args.updated_by, ) if mgr is not None: try: mgr._set_to_redis(key, meta.get("value")) mgr._cache[key] = meta.get("value") except Exception: pass ok += 1 except Exception as e: fail += 1 print(f"[失败] {key}: {e}") print(f"\n完成:成功 {ok},失败 {fail}") if fail > 0: sys.exit(1) if __name__ == "__main__": main()