新增功能

This commit is contained in:
Your Name
2026-07-28 09:46:53 +08:00
parent 45b3bc0852
commit 980795b4da
57 changed files with 18421 additions and 1051 deletions
+28 -15
View File
@@ -42,11 +42,21 @@ _STORE = ConversationStore(os.path.join(_ROOT, "conversations.json"))
def _mask_key(key: str) -> str:
if not key or len(key) < 10:
if not key:
return ""
if len(key) < 10:
return "***"
return key[:6] + "" + key[-4:]
def _is_secret_config_key(key: str) -> bool:
upper = str(key).upper()
return any(
marker in upper
for marker in ("KEY", "TOKEN", "SECRET", "PASSWORD", "CREDENTIAL")
)
def _reload_store() -> ConversationStore:
"""每次读取前重新加载,避免外部进程写盘后读到旧缓存。"""
global _STORE
@@ -115,12 +125,13 @@ def get_status() -> dict[str, Any]:
@mcp.tool()
def get_ai_config(reveal_api_key: bool = False) -> dict[str, Any]:
"""读取当前 AI 配置(默认脱敏 API Keyreveal_api_key=true 时显示完整 Key"""
def get_ai_config() -> dict[str, Any]:
"""读取当前 AI 配置;所有密码、Key、Token 和 Secret 始终脱敏"""
ai_config.load_settings()
data = {k: getattr(ai_config, k) for k in ai_config.CONFIGURABLE_KEYS}
if not reveal_api_key and "AI_API_KEY" in data:
data["AI_API_KEY"] = _mask_key(str(data["AI_API_KEY"]))
for key in tuple(data):
if _is_secret_config_key(key):
data[key] = _mask_key(str(data[key] or ""))
data["system_prompt_preview"] = ai_config.build_system_prompt()[:500]
return data
@@ -128,7 +139,7 @@ def get_ai_config(reveal_api_key: bool = False) -> dict[str, Any]:
@mcp.tool()
def update_ai_config(updates: dict[str, Any]) -> dict[str, Any]:
"""
更新 AI 配置并写入 ai_settings.json。
更新 AI 配置并写入 ai_settings.local.json。
只允许修改 CONFIGURABLE_KEYS 中的字段,例如:
{"AI_AGENT_NAME": "高兴亮", "AI_COUNTER_INSULT_ENABLED": false, "AI_TEMPERATURE": 0.8}
"""
@@ -136,7 +147,7 @@ def update_ai_config(updates: dict[str, Any]) -> dict[str, Any]:
changed = {}
ignored = []
for k, v in (updates or {}).items():
if k not in ai_config.CONFIGURABLE_KEYS:
if k not in ai_config.CONFIGURABLE_KEYS or _is_secret_config_key(k):
ignored.append(k)
continue
# 轻量类型校正
@@ -156,13 +167,9 @@ def update_ai_config(updates: dict[str, Any]) -> dict[str, Any]:
except Exception:
ignored.append(k)
continue
setattr(ai_config, k, v)
changed[k] = v if k != "AI_API_KEY" else _mask_key(str(v))
changed[k] = v
if "AI_AGENT_NAME" in changed or "AI_HOSPITAL_NAME" in changed:
ai_config.AI_SYSTEM_PROMPT = ai_config.build_system_prompt()
ai_config.save_settings()
ai_config.apply_settings(changed, persist=True)
return {"ok": True, "changed": changed, "ignored": ignored}
@@ -240,7 +247,13 @@ def draft_reply(
history = store.history(session_id)
try:
reply = call_ai_text(message.strip(), history=history)
reply = call_ai_text(
message.strip(),
history=history,
# use_history=False must also disable the Chat project's remote
# conversation, not merely omit the local archive.
session_id=session_id if use_history else None,
)
except Exception as e:
return {"ok": False, "error": str(e)}
@@ -299,7 +312,7 @@ def resource_sessions() -> str:
@mcp.resource("wechat-rpa://config")
def resource_config() -> str:
"""AI 配置 JSONKey 脱敏)。"""
return json.dumps(get_ai_config(False), ensure_ascii=False, indent=2)
return json.dumps(get_ai_config(), ensure_ascii=False, indent=2)
@mcp.prompt()