feat: 实现AI拒答机制和语言控制优化

- 添加 RunStatus.REFUSED 状态,AI可明确表达拒答意图
- 优化 System Prompt 使用视觉强调提高AI对拒答规则的遵守
- User Prompt 添加 SCOPE CHECK 和语言约束
- Worker Rules 添加多语言版本角色扮演规则
- Runner 传递 language 参数到 worker stage
- json_finalize 添加语言约束参数
- 更新单元测试匹配新的 prompt 结构
This commit is contained in:
ZL-Q
2026-04-29 01:38:59 +08:00
parent adb2b3bcc3
commit f497afbff2
15 changed files with 1293 additions and 117 deletions
+42 -7
View File
@@ -2,30 +2,48 @@ from __future__ import annotations
from core.agentscope.prompts.agent_prompt import build_agent_prompt
from core.agentscope.prompts.system_prompt import build_system_prompt
from core.agentscope.prompts.user_prompt import (
build_divination_user_prompt,
build_follow_up_user_prompt,
)
from schemas.agent.system_agent import AgentType, SystemAgentLLMConfig
def test_system_prompt_enforces_language_en() -> None:
def test_system_prompt_safety_has_refusal_rules_en() -> None:
prompt = build_system_prompt(
agent_type=AgentType.WORKER,
language="en-US",
llm_config=SystemAgentLLMConfig(),
)
assert "English" in prompt
assert "<!-- SAFETY_START -->" in prompt
assert "<!-- OUTPUT_START -->" in prompt
assert "REFUSE IMMEDIATELY" in prompt
assert "Tarot" in prompt
assert "Ba Zi" in prompt
def test_system_prompt_enforces_language_zh_cn() -> None:
def test_system_prompt_safety_has_refusal_rules_zh() -> None:
prompt = build_system_prompt(
agent_type=AgentType.WORKER,
language="zh-CN",
llm_config=SystemAgentLLMConfig(),
)
assert "简体中文" in prompt
assert "<!-- SAFETY_START -->" in prompt
assert "必须立即拒绝" in prompt
assert "塔罗" in prompt
assert "八字" in prompt
def test_system_prompt_no_language_constraint_in_system() -> None:
prompt = build_system_prompt(
agent_type=AgentType.WORKER,
language="en-US",
llm_config=SystemAgentLLMConfig(),
)
assert "<!-- OUTPUT_START -->" not in prompt
assert "MUST respond in" not in prompt
def test_system_prompt_safety_restricts_to_divination() -> None:
@@ -35,7 +53,7 @@ def test_system_prompt_safety_restricts_to_divination() -> None:
llm_config=SystemAgentLLMConfig(),
)
assert "只回答与六爻占卜" in prompt or "解卦" in prompt
assert "六爻" in prompt or "解卦" in prompt
def test_system_prompt_does_not_contain_env_section() -> None:
@@ -54,6 +72,7 @@ def test_agent_prompt_keeps_only_identity_and_domain_flow() -> None:
prompt = build_agent_prompt(
agent_type=AgentType.WORKER,
llm_config=SystemAgentLLMConfig(),
language="zh-CN",
)
assert "focus_points" in prompt
@@ -71,13 +90,29 @@ def test_system_prompt_sections_are_not_duplicated() -> None:
assert prompt.count("<!-- SAFETY_START -->") == 1
assert prompt.count("<!-- AGENT_START -->") == 1
assert prompt.count("<!-- OUTPUT_START -->") == 1
def test_system_prompt_requires_paragraph_breaks_for_answer() -> None:
prompt = build_agent_prompt(
agent_type=AgentType.WORKER,
llm_config=SystemAgentLLMConfig(),
language="zh-CN",
)
assert "段间用\\n\\n" in prompt
def test_user_prompt_has_language_constraint_en() -> None:
prompt = build_follow_up_user_prompt(question="test question", language="en-US")
assert "CRITICAL: YOUR ENTIRE RESPONSE MUST BE IN ENGLISH" in prompt
assert "═══════════════════════════════════════════════════════════════════════════════" in prompt
assert "[SCOPE CHECK - REFUSE IF:]" in prompt
def test_user_prompt_has_language_constraint_zh() -> None:
prompt = build_follow_up_user_prompt(question="test question", language="zh-CN")
assert "关键:必须全程使用简体中文回答" in prompt
assert "═══════════════════════════════════════════════════════════════════════════════" in prompt
assert "【范围检查" in prompt
+31 -2
View File
@@ -47,12 +47,41 @@ class _Model:
return _Response(self._payload)
def test_build_instruction_uses_output_schema_title() -> None:
def test_build_instruction_has_schema() -> None:
instruction = build_json_finalize_instruction(
schema_json="{}",
attempt=1,
)
assert "[输出结构Output Schema]" in instruction
assert "[Output Schema]" in instruction
def test_build_instruction_has_language_constraint_en() -> None:
instruction = build_json_finalize_instruction(
schema_json="{}",
attempt=1,
language="en-US",
)
assert "ENGLISH OUTPUT REQUIRED" in instruction
assert "═══════════════════════════════════════════════════════════════════════════════" in instruction
def test_build_instruction_has_language_constraint_zh() -> None:
instruction = build_json_finalize_instruction(
schema_json="{}",
attempt=1,
language="zh-CN",
)
assert "返回 JSON。使用简体中文" in instruction
def test_build_instruction_no_language_constraint_when_none() -> None:
instruction = build_json_finalize_instruction(
schema_json="{}",
attempt=1,
language=None,
)
assert "ENGLISH OUTPUT REQUIRED" not in instruction
assert "返回 JSON" not in instruction
@pytest.mark.asyncio