update:1.开放系统内置提示词,支持用户自定义模板
This commit is contained in:
@@ -851,7 +851,510 @@ class PromptService:
|
||||
1. 只返回纯JSON对象,不要有```json```这样的标记
|
||||
2. 所有内容描述中严禁使用任何特殊符号
|
||||
3. 不要有任何额外的文字说明"""
|
||||
|
||||
# 情节分析提示词
|
||||
PLOT_ANALYSIS = """你是一位专业的小说编辑和剧情分析师。请深度分析以下章节内容:
|
||||
|
||||
**章节信息:**
|
||||
- 章节: 第{chapter_number}章
|
||||
- 标题: {title}
|
||||
- 字数: {word_count}字
|
||||
|
||||
**章节内容:**
|
||||
{content}
|
||||
|
||||
---
|
||||
|
||||
**分析任务:**
|
||||
请从专业编辑的角度,全面分析这一章节:
|
||||
|
||||
### 1. 剧情钩子 (Hooks) - 吸引读者的元素
|
||||
识别能够吸引读者继续阅读的关键元素:
|
||||
- **悬念钩子**: 未解之谜、疑问、谜团
|
||||
- **情感钩子**: 引发共鸣的情感点、触动心弦的时刻
|
||||
- **冲突钩子**: 矛盾对抗、紧张局势
|
||||
- **认知钩子**: 颠覆认知的信息、惊人真相
|
||||
|
||||
每个钩子需要:
|
||||
- 类型分类
|
||||
- 具体内容描述
|
||||
- 强度评分(1-10)
|
||||
- 出现位置(开头/中段/结尾)
|
||||
- **关键词**: 【必填】从章节原文中逐字复制一段关键文本(8-25字),必须是原文中真实存在的连续文字,用于在文本中精确定位。不要概括或改写,必须原样复制!
|
||||
|
||||
### 2. 伏笔分析 (Foreshadowing)
|
||||
- **埋下的新伏笔**: 描述内容、预期作用、隐藏程度(1-10)
|
||||
- **回收的旧伏笔**: 呼应哪一章、回收效果评分
|
||||
- **伏笔质量**: 巧妙性和合理性评估
|
||||
- **关键词**: 【必填】从章节原文中逐字复制一段关键文本(8-25字),必须是原文中真实存在的连续文字,用于在文本中精确定位。不要概括或改写,必须原样复制!
|
||||
|
||||
### 3. 冲突分析 (Conflict)
|
||||
- 冲突类型: 人与人/人与己/人与环境/人与社会
|
||||
- 冲突各方及其立场
|
||||
- 冲突强度评分(1-10)
|
||||
- 冲突解决进度(0-100%)
|
||||
|
||||
### 4. 情感曲线 (Emotional Arc)
|
||||
- 主导情绪: 紧张/温馨/悲伤/激昂/平静等
|
||||
- 情感强度(1-10)
|
||||
- 情绪变化轨迹描述
|
||||
|
||||
### 5. 角色状态追踪 (Character Development)
|
||||
对每个出场角色分析:
|
||||
- 心理状态变化(前→后)
|
||||
- 关系变化
|
||||
- 关键行动和决策
|
||||
- 成长或退步
|
||||
|
||||
### 6. 关键情节点 (Plot Points)
|
||||
列出3-5个核心情节点:
|
||||
- 情节内容
|
||||
- 类型(revelation/conflict/resolution/transition)
|
||||
- 重要性(0.0-1.0)
|
||||
- 对故事的影响
|
||||
- **关键词**: 【必填】从章节原文中逐字复制一段关键文本(8-25字),必须是原文中真实存在的连续文字,用于在文本中精确定位。不要概括或改写,必须原样复制!
|
||||
|
||||
### 7. 场景与节奏
|
||||
- 主要场景
|
||||
- 叙事节奏(快/中/慢)
|
||||
- 对话与描写的比例
|
||||
|
||||
### 8. 质量评分
|
||||
- 节奏把控: 1-10分
|
||||
- 吸引力: 1-10分
|
||||
- 连贯性: 1-10分
|
||||
- 整体质量: 1-10分
|
||||
|
||||
### 9. 改进建议
|
||||
提供3-5条具体的改进建议
|
||||
|
||||
---
|
||||
|
||||
**输出格式(纯JSON,不要markdown标记):**
|
||||
|
||||
{{
|
||||
"hooks": [
|
||||
{{
|
||||
"type": "悬念",
|
||||
"content": "具体描述",
|
||||
"strength": 8,
|
||||
"position": "中段",
|
||||
"keyword": "必须从原文逐字复制的文本片段"
|
||||
}}
|
||||
],
|
||||
"foreshadows": [
|
||||
{{
|
||||
"content": "伏笔内容",
|
||||
"type": "planted",
|
||||
"strength": 7,
|
||||
"subtlety": 8,
|
||||
"reference_chapter": null,
|
||||
"keyword": "必须从原文逐字复制的文本片段"
|
||||
}}
|
||||
],
|
||||
"conflict": {{
|
||||
"types": ["人与人", "人与己"],
|
||||
"parties": ["主角-复仇", "反派-维护现状"],
|
||||
"level": 8,
|
||||
"description": "冲突描述",
|
||||
"resolution_progress": 0.3
|
||||
}},
|
||||
"emotional_arc": {{
|
||||
"primary_emotion": "紧张",
|
||||
"intensity": 8,
|
||||
"curve": "平静→紧张→高潮→释放",
|
||||
"secondary_emotions": ["期待", "焦虑"]
|
||||
}},
|
||||
"character_states": [
|
||||
{{
|
||||
"character_name": "张三",
|
||||
"state_before": "犹豫",
|
||||
"state_after": "坚定",
|
||||
"psychological_change": "心理变化描述",
|
||||
"key_event": "触发事件",
|
||||
"relationship_changes": {{"李四": "关系改善"}}
|
||||
}}
|
||||
],
|
||||
"plot_points": [
|
||||
{{
|
||||
"content": "情节点描述",
|
||||
"type": "revelation",
|
||||
"importance": 0.9,
|
||||
"impact": "推动故事发展",
|
||||
"keyword": "必须从原文逐字复制的文本片段"
|
||||
}}
|
||||
],
|
||||
"scenes": [
|
||||
{{
|
||||
"location": "地点",
|
||||
"atmosphere": "氛围",
|
||||
"duration": "时长估计"
|
||||
}}
|
||||
],
|
||||
"pacing": "varied",
|
||||
"dialogue_ratio": 0.4,
|
||||
"description_ratio": 0.3,
|
||||
"scores": {{
|
||||
"pacing": 8,
|
||||
"engagement": 9,
|
||||
"coherence": 8,
|
||||
"overall": 8.5
|
||||
}},
|
||||
"plot_stage": "发展",
|
||||
"suggestions": [
|
||||
"具体建议1",
|
||||
"具体建议2"
|
||||
]
|
||||
}}
|
||||
|
||||
**重要提示:**
|
||||
1. 每个钩子、伏笔、情节点的keyword字段是必填的,不能为空
|
||||
2. keyword必须是从章节原文中逐字复制的文本,长度8-25字
|
||||
3. keyword用于在前端标注文本位置,所以必须能在原文中精确找到
|
||||
4. 不要使用概括性语句或改写后的文字作为keyword
|
||||
|
||||
只返回JSON,不要其他说明。"""
|
||||
|
||||
# 大纲单批次展开提示词
|
||||
PLOT_EXPANSION_SINGLE_BATCH = """你是专业的小说情节架构师。请分析以下大纲节点,将其展开为 {target_chapter_count} 个章节的详细规划。
|
||||
|
||||
【项目信息】
|
||||
小说名称:{project_title}
|
||||
类型:{project_genre}
|
||||
主题:{project_theme}
|
||||
叙事视角:{project_narrative_perspective}
|
||||
|
||||
【世界观背景】
|
||||
时间背景:{project_world_time_period}
|
||||
地理位置:{project_world_location}
|
||||
氛围基调:{project_world_atmosphere}
|
||||
|
||||
【角色信息】
|
||||
{characters_info}
|
||||
|
||||
【当前大纲节点 - 展开对象】
|
||||
序号:第 {outline_order_index} 节
|
||||
标题:{outline_title}
|
||||
内容:{outline_content}
|
||||
|
||||
【上下文参考】
|
||||
{context_info}
|
||||
|
||||
【展开策略】
|
||||
{strategy_instruction}
|
||||
|
||||
【⚠️ 重要约束 - 必须严格遵守】
|
||||
1. **内容边界约束**:
|
||||
- ✅ 只能展开【当前大纲节点】中明确描述的内容
|
||||
- ❌ 绝对不能推进到后续大纲的内容(如果有【后一节】信息)
|
||||
- ❌ 不要让剧情快速推进,要深化而非跨越
|
||||
|
||||
2. **展开原则**:
|
||||
- 将当前大纲的单一事件拆解为多个细节丰富的章节
|
||||
- 深入挖掘情感、心理、环境、对话等细节
|
||||
- 放慢叙事节奏,让读者充分体验当前阶段的剧情
|
||||
- 每个章节都应该是当前大纲内容的不同侧面或阶段
|
||||
|
||||
3. **如何避免剧情越界**:
|
||||
- 如果当前大纲描述"主角遇到困境",展开时应详写困境的发现、分析、情感冲击等
|
||||
- 不要直接写到"解决困境",除非原大纲明确包含解决过程
|
||||
- 如果看到【后一节】的内容,那些是禁区,绝不提前展开
|
||||
|
||||
【任务要求】
|
||||
1. 深度分析该大纲的剧情容量和叙事节奏
|
||||
2. 识别关键剧情点、冲突点和情感转折点(仅限当前大纲范围内)
|
||||
3. 将大纲拆解为 {target_chapter_count} 个章节,每章需包含:
|
||||
- sub_index: 子章节序号(1, 2, 3...)
|
||||
- title: 章节标题(体现该章核心冲突或情感)
|
||||
- plot_summary: 剧情摘要(200-300字,详细描述该章发生的事件,仅限当前大纲内容)
|
||||
- key_events: 关键事件列表(3-5个关键剧情点,必须在当前大纲范围内)
|
||||
- character_focus: 角色焦点(主要涉及的角色名称)
|
||||
- emotional_tone: 情感基调(如:紧张、温馨、悲伤、激动等)
|
||||
- narrative_goal: 叙事目标(该章要达成的叙事效果)
|
||||
- conflict_type: 冲突类型(如:内心挣扎、人际冲突、环境挑战等)
|
||||
- estimated_words: 预计字数(建议2000-5000字)
|
||||
{scene_instruction}
|
||||
4. 确保章节间:
|
||||
- 衔接自然流畅
|
||||
- 剧情递进合理(但不超出当前大纲边界)
|
||||
- 节奏张弛有度
|
||||
- 每章都有明确的叙事价值
|
||||
- 最后一章结束时,剧情发展程度应恰好完成当前大纲描述的内容,不多不少
|
||||
|
||||
【输出格式】
|
||||
请严格按照以下JSON数组格式输出,不要添加任何其他文字:
|
||||
[
|
||||
{{
|
||||
"sub_index": 1,
|
||||
"title": "章节标题",
|
||||
"plot_summary": "该章详细剧情摘要...",
|
||||
"key_events": ["关键事件1", "关键事件2", "关键事件3"],
|
||||
"character_focus": ["角色A", "角色B"],
|
||||
"emotional_tone": "情感基调",
|
||||
"narrative_goal": "叙事目标",
|
||||
"conflict_type": "冲突类型",
|
||||
"estimated_words": 3000{scene_field}
|
||||
}}
|
||||
]
|
||||
|
||||
请开始分析并生成章节规划:
|
||||
"""
|
||||
|
||||
# 大纲分批展开提示词
|
||||
PLOT_EXPANSION_MULTI_BATCH = """你是专业的小说情节架构师。请继续分析以下大纲节点,将其展开为第{start_index}-{end_index}节(共{target_chapter_count}个章节)的详细规划。
|
||||
|
||||
【项目信息】
|
||||
小说名称:{project_title}
|
||||
类型:{project_genre}
|
||||
主题:{project_theme}
|
||||
叙事视角:{project_narrative_perspective}
|
||||
|
||||
【世界观背景】
|
||||
时间背景:{project_world_time_period}
|
||||
地理位置:{project_world_location}
|
||||
氛围基调:{project_world_atmosphere}
|
||||
|
||||
【角色信息】
|
||||
{characters_info}
|
||||
|
||||
【当前大纲节点 - 展开对象】
|
||||
序号:第 {outline_order_index} 节
|
||||
标题:{outline_title}
|
||||
内容:{outline_content}
|
||||
|
||||
【上下文参考】
|
||||
{context_info}
|
||||
{previous_context}
|
||||
|
||||
【展开策略】
|
||||
{strategy_instruction}
|
||||
|
||||
【⚠️ 重要约束 - 必须严格遵守】
|
||||
1. **内容边界约束**:
|
||||
- ✅ 只能展开【当前大纲节点】中明确描述的内容
|
||||
- ❌ 绝对不能推进到后续大纲的内容(如果有【后一节】信息)
|
||||
- ❌ 不要让剧情快速推进,要深化而非跨越
|
||||
|
||||
2. **分批连续性约束**:
|
||||
- 这是第{start_index}-{end_index}节,是整个展开的一部分
|
||||
- 必须与前面已生成的章节自然衔接
|
||||
- 从第{start_index}节开始编号(sub_index从{start_index}开始)
|
||||
- 继续深化当前大纲的内容,保持叙事连贯性
|
||||
|
||||
3. **展开原则**:
|
||||
- 将当前大纲的单一事件拆解为多个细节丰富的章节
|
||||
- 深入挖掘情感、心理、环境、对话等细节
|
||||
- 放慢叙事节奏,让读者充分体验当前阶段的剧情
|
||||
- 每个章节都应该是当前大纲内容的不同侧面或阶段
|
||||
|
||||
【任务要求】
|
||||
1. 深度分析该大纲的剧情容量和叙事节奏
|
||||
2. 识别关键剧情点、冲突点和情感转折点(仅限当前大纲范围内)
|
||||
3. 生成第{start_index}-{end_index}节的章节规划,每章需包含:
|
||||
- sub_index: 子章节序号(从{start_index}开始)
|
||||
- title: 章节标题(体现该章核心冲突或情感)
|
||||
- plot_summary: 剧情摘要(200-300字,详细描述该章发生的事件)
|
||||
- key_events: 关键事件列表(3-5个关键剧情点)
|
||||
- character_focus: 角色焦点(主要涉及的角色名称)
|
||||
- emotional_tone: 情感基调(如:紧张、温馨、悲伤、激动等)
|
||||
- narrative_goal: 叙事目标(该章要达成的叙事效果)
|
||||
- conflict_type: 冲突类型(如:内心挣扎、人际冲突、环境挑战等)
|
||||
- estimated_words: 预计字数(建议2000-5000字)
|
||||
{scene_instruction}
|
||||
4. 确保章节间:
|
||||
- 与前面章节衔接自然流畅
|
||||
- 剧情递进合理(但不超出当前大纲边界)
|
||||
- 节奏张弛有度
|
||||
- 每章都有明确的叙事价值
|
||||
|
||||
【输出格式】
|
||||
请严格按照以下JSON数组格式输出,不要添加任何其他文字:
|
||||
[
|
||||
{{
|
||||
"sub_index": {start_index},
|
||||
"title": "章节标题",
|
||||
"plot_summary": "该章详细剧情摘要...",
|
||||
"key_events": ["关键事件1", "关键事件2", "关键事件3"],
|
||||
"character_focus": ["角色A", "角色B"],
|
||||
"emotional_tone": "情感基调",
|
||||
"narrative_goal": "叙事目标",
|
||||
"conflict_type": "冲突类型",
|
||||
"estimated_words": 3000{scene_field}
|
||||
}}
|
||||
]
|
||||
|
||||
请开始分析并生成第{start_index}-{end_index}节的章节规划:
|
||||
"""
|
||||
|
||||
# 章节重写系统提示词
|
||||
CHAPTER_REGENERATION_SYSTEM = """你是一位经验丰富的专业小说编辑和作家。现在需要根据反馈意见重新创作一个章节。
|
||||
|
||||
你的任务是:
|
||||
1. 仔细理解原始章节的内容和意图
|
||||
2. 认真分析所有的修改要求
|
||||
3. 在保持故事连贯性的前提下,创作一个改进后的新版本
|
||||
4. 确保新版本在艺术性和可读性上都有明显提升
|
||||
|
||||
---
|
||||
"""
|
||||
# MCP工具测试提示词
|
||||
MCP_TOOL_TEST = """你是MCP插件测试助手,需要测试插件 '{plugin_name}' 的功能。
|
||||
|
||||
⚠️ 重要规则:生成参数时,必须严格使用工具 schema 中定义的原始参数名称,不要转换为 snake_case 或其他格式。
|
||||
例如:如果 schema 中是 'nextThoughtNeeded',就必须使用 'nextThoughtNeeded',不能改成 'next_thought_needed'。
|
||||
|
||||
请选择一个合适的工具进行测试,优先选择搜索、查询类工具。
|
||||
生成真实有效的测试参数(例如搜索"人工智能最新进展"而不是"test")。
|
||||
|
||||
现在开始测试这个插件。"""
|
||||
|
||||
MCP_TOOL_TEST_SYSTEM = """你是专业的API测试工具。当给定工具列表时,选择一个工具并使用合适的参数调用它。
|
||||
|
||||
⚠️ 关键规则:调用工具时,必须严格使用 schema 中定义的原始参数名,不要自行转换命名风格。
|
||||
- 如果参数名是 camelCase(如 nextThoughtNeeded),就使用 camelCase
|
||||
- 如果参数名是 snake_case(如 next_thought),就使用 snake_case
|
||||
- 保持与 schema 中定义的完全一致,包括大小写和命名风格"""
|
||||
|
||||
# 灵感模式提示词字典
|
||||
INSPIRATION_PROMPTS = {
|
||||
"title": {
|
||||
"system": """你是一位专业的小说创作顾问。
|
||||
用户的原始想法:{initial_idea}
|
||||
|
||||
请根据用户的想法,生成6个吸引人的书名建议,要求:
|
||||
1. 紧扣用户的原始想法和核心故事构思
|
||||
2. 富有创意和吸引力
|
||||
3. 涵盖不同的风格倾向
|
||||
|
||||
返回JSON格式:
|
||||
{{
|
||||
"prompt": "根据你的想法,我为你准备了几个书名建议:",
|
||||
"options": ["书名1", "书名2", "书名3", "书名4", "书名5", "书名6"]
|
||||
}}
|
||||
|
||||
只返回纯JSON,不要有其他文字。""",
|
||||
"user": "用户的想法:{initial_idea}\n请生成6个书名建议"
|
||||
},
|
||||
"description": {
|
||||
"system": """你是一位专业的小说创作顾问。
|
||||
用户的原始想法:{initial_idea}
|
||||
已确定的书名:{title}
|
||||
|
||||
请生成6个精彩的小说简介,要求:
|
||||
1. 必须紧扣用户的原始想法,确保简介是原始想法的具体展开
|
||||
2. 符合已确定的书名风格
|
||||
3. 简洁有力,每个50-100字
|
||||
4. 包含核心冲突
|
||||
5. 涵盖不同的故事走向,但都基于用户的原始构思
|
||||
|
||||
返回JSON格式:
|
||||
{{"prompt":"选择一个简介:","options":["简介1","简介2","简介3","简介4","简介5","简介6"]}}
|
||||
|
||||
只返回纯JSON,不要有其他文字,不要换行。""",
|
||||
"user": "原始想法:{initial_idea}\n书名:{title}\n请生成6个简介选项"
|
||||
},
|
||||
"theme": {
|
||||
"system": """你是一位专业的小说创作顾问。
|
||||
用户的原始想法:{initial_idea}
|
||||
小说信息:
|
||||
- 书名:{title}
|
||||
- 简介:{description}
|
||||
|
||||
请生成6个深刻的主题选项,要求:
|
||||
1. 必须与用户的原始想法保持高度一致
|
||||
2. 符合书名和简介的风格
|
||||
3. 有深度和思想性
|
||||
4. 每个50-150字
|
||||
5. 涵盖不同角度(如:成长、复仇、救赎、探索等),但都围绕用户的核心构思
|
||||
|
||||
返回JSON格式:
|
||||
{{"prompt":"这本书的核心主题是什么?","options":["主题1","主题2","主题3","主题4","主题5","主题6"]}}
|
||||
|
||||
只返回纯JSON,不要有其他文字,不要换行。""",
|
||||
"user": "原始想法:{initial_idea}\n书名:{title}\n简介:{description}\n请生成6个主题选项"
|
||||
},
|
||||
"genre": {
|
||||
"system": """你是一位专业的小说创作顾问。
|
||||
用户的原始想法:{initial_idea}
|
||||
小说信息:
|
||||
- 书名:{title}
|
||||
- 简介:{description}
|
||||
- 主题:{theme}
|
||||
|
||||
请生成6个合适的类型标签(每个2-4字),要求:
|
||||
1. 必须符合用户原始想法中暗示的类型倾向
|
||||
2. 符合小说整体风格
|
||||
3. 可以多选组合
|
||||
|
||||
常见类型:玄幻、都市、科幻、武侠、仙侠、历史、言情、悬疑、奇幻、修仙等
|
||||
|
||||
返回JSON格式:
|
||||
{{"prompt":"选择类型标签(可多选):","options":["类型1","类型2","类型3","类型4","类型5","类型6"]}}
|
||||
|
||||
只返回紧凑的纯JSON,不要换行,不要有其他文字。""",
|
||||
"user": "原始想法:{initial_idea}\n书名:{title}\n简介:{description}\n主题:{theme}\n请生成6个类型标签"
|
||||
}
|
||||
}
|
||||
|
||||
# 灵感模式智能补全提示词
|
||||
INSPIRATION_QUICK_COMPLETE = """你是一位专业的小说创作顾问。用户提供了部分小说信息,请补全缺失的字段。
|
||||
|
||||
用户已提供的信息:
|
||||
{existing}
|
||||
|
||||
请生成完整的小说方案,包含:
|
||||
1. title: 书名(3-6字,如果用户已提供则保持原样)
|
||||
2. description: 简介(50-100字,必须基于用户提供的信息,不要偏离原意)
|
||||
3. theme: 核心主题(30-50字,必须与用户提供的信息保持一致)
|
||||
4. genre: 类型标签数组(2-3个)
|
||||
|
||||
重要:所有补全的内容都必须与用户提供的信息保持高度关联,确保前后一致性。
|
||||
|
||||
返回JSON格式:
|
||||
{{
|
||||
"title": "书名",
|
||||
"description": "简介内容...",
|
||||
"theme": "主题内容...",
|
||||
"genre": ["类型1", "类型2"]
|
||||
}}
|
||||
|
||||
只返回纯JSON,不要有其他文字。"""
|
||||
# 世界观资料收集提示词(MCP增强用)
|
||||
MCP_WORLD_BUILDING_PLANNING = """你正在为小说《{title}》设计世界观。
|
||||
|
||||
【小说信息】
|
||||
- 题材:{genre}
|
||||
- 主题:{theme}
|
||||
- 简介:{description}
|
||||
|
||||
【任务】
|
||||
请使用可用工具搜索相关背景资料,帮助构建更真实、更有深度的世界观设定。
|
||||
你可以查询:
|
||||
1. 历史背景(如果是历史题材)
|
||||
2. 地理环境和文化特征
|
||||
3. 相关领域的专业知识
|
||||
4. 类似作品的设定参考
|
||||
|
||||
请查询最关键的1个问题(不要超过1个)。"""
|
||||
|
||||
# 角色资料收集提示词(MCP增强用)
|
||||
MCP_CHARACTER_PLANNING = """你正在为小说《{title}》设计角色。
|
||||
|
||||
【小说信息】
|
||||
- 题材:{genre}
|
||||
- 主题:{theme}
|
||||
- 时代背景:{time_period}
|
||||
- 地理位置:{location}
|
||||
|
||||
【任务】
|
||||
请使用可用工具搜索相关参考资料,帮助设计更真实、更有深度的角色。
|
||||
你可以查询:
|
||||
1. 该时代/地域的真实历史人物特征
|
||||
2. 文化背景和社会习俗
|
||||
3. 职业特点和生活方式
|
||||
4. 相关领域的人物原型
|
||||
|
||||
请查询最关键的1个问题(不要超过1个)。"""
|
||||
# 大纲展开为多章节的提示词
|
||||
OUTLINE_EXPANSION = """你是专业的小说情节架构师。请分析以下大纲节点,将其展开为 {target_chapters} 个章节的详细规划。
|
||||
|
||||
@@ -1339,7 +1842,417 @@ class PromptService:
|
||||
scene_instruction=scene_instruction,
|
||||
scene_field=scene_field
|
||||
)
|
||||
|
||||
@classmethod
|
||||
def get_plot_analysis_prompt(cls, chapter_number: int, title: str,
|
||||
content: str, word_count: int) -> str:
|
||||
"""获取章节剧情分析提示词"""
|
||||
return cls.format_prompt(
|
||||
cls.PLOT_ANALYSIS,
|
||||
chapter_number=chapter_number,
|
||||
title=title,
|
||||
content=content,
|
||||
word_count=word_count
|
||||
)
|
||||
@classmethod
|
||||
def get_plot_expansion_single_batch_prompt(cls, project_title: str, project_genre: str, project_theme: str,
|
||||
project_narrative_perspective: str, project_world_time_period: str,
|
||||
project_world_location: str, project_world_atmosphere: str,
|
||||
characters_info: str, outline_order_index: int, outline_title: str,
|
||||
outline_content: str, context_info: str, strategy_instruction: str,
|
||||
target_chapter_count: int, scene_instruction: str, scene_field: str) -> str:
|
||||
"""获取大纲单批次展开提示词"""
|
||||
return cls.format_prompt(
|
||||
cls.PLOT_EXPANSION_SINGLE_BATCH,
|
||||
project_title=project_title, project_genre=project_genre, project_theme=project_theme,
|
||||
project_narrative_perspective=project_narrative_perspective, project_world_time_period=project_world_time_period,
|
||||
project_world_location=project_world_location, project_world_atmosphere=project_world_atmosphere,
|
||||
characters_info=characters_info, outline_order_index=outline_order_index, outline_title=outline_title,
|
||||
outline_content=outline_content, context_info=context_info, strategy_instruction=strategy_instruction,
|
||||
target_chapter_count=target_chapter_count, scene_instruction=scene_instruction, scene_field=scene_field
|
||||
)
|
||||
|
||||
@classmethod
|
||||
def get_plot_expansion_multi_batch_prompt(cls, project_title: str, project_genre: str, project_theme: str,
|
||||
project_narrative_perspective: str, project_world_time_period: str,
|
||||
project_world_location: str, project_world_atmosphere: str,
|
||||
characters_info: str, outline_order_index: int, outline_title: str,
|
||||
outline_content: str, context_info: str, previous_context: str,
|
||||
strategy_instruction: str, start_index: int, end_index: int,
|
||||
target_chapter_count: int, scene_instruction: str, scene_field: str) -> str:
|
||||
"""获取大纲分批展开提示词"""
|
||||
return cls.format_prompt(
|
||||
cls.PLOT_EXPANSION_MULTI_BATCH,
|
||||
project_title=project_title, project_genre=project_genre, project_theme=project_theme,
|
||||
project_narrative_perspective=project_narrative_perspective, project_world_time_period=project_world_time_period,
|
||||
project_world_location=project_world_location, project_world_atmosphere=project_world_atmosphere,
|
||||
characters_info=characters_info, outline_order_index=outline_order_index, outline_title=outline_title,
|
||||
outline_content=outline_content, context_info=context_info, previous_context=previous_context,
|
||||
strategy_instruction=strategy_instruction, start_index=start_index, end_index=end_index,
|
||||
target_chapter_count=target_chapter_count, scene_instruction=scene_instruction, scene_field=scene_field
|
||||
)
|
||||
|
||||
@classmethod
|
||||
def get_chapter_regeneration_prompt(cls, chapter_number: int, title: str, word_count: int, content: str,
|
||||
modification_instructions: str, project_context: Dict[str, Any],
|
||||
style_content: str, target_word_count: int) -> str:
|
||||
"""获取章节重写提示词"""
|
||||
prompt_parts = [cls.CHAPTER_REGENERATION_SYSTEM]
|
||||
|
||||
# 原始章节信息
|
||||
prompt_parts.append(f"""## 📖 原始章节信息
|
||||
|
||||
**章节**:第{chapter_number}章
|
||||
**标题**:{title}
|
||||
**字数**:{word_count}字
|
||||
|
||||
**原始内容**:
|
||||
{content}
|
||||
|
||||
---
|
||||
""")
|
||||
|
||||
# 修改指令
|
||||
prompt_parts.append(modification_instructions)
|
||||
prompt_parts.append("\n---\n")
|
||||
|
||||
# 项目背景信息
|
||||
prompt_parts.append(f"""## 🌍 项目背景信息
|
||||
|
||||
**小说标题**:{project_context.get('project_title', '未知')}
|
||||
**题材**:{project_context.get('genre', '未设定')}
|
||||
**主题**:{project_context.get('theme', '未设定')}
|
||||
**叙事视角**:{project_context.get('narrative_perspective', '第三人称')}
|
||||
**世界观设定**:
|
||||
- 时代背景:{project_context.get('time_period', '未设定')}
|
||||
- 地理位置:{project_context.get('location', '未设定')}
|
||||
- 氛围基调:{project_context.get('atmosphere', '未设定')}
|
||||
|
||||
---
|
||||
""")
|
||||
|
||||
# 角色信息
|
||||
if project_context.get('characters_info'):
|
||||
prompt_parts.append(f"""## 👥 角色信息
|
||||
|
||||
{project_context['characters_info']}
|
||||
|
||||
---
|
||||
""")
|
||||
|
||||
# 章节大纲
|
||||
if project_context.get('chapter_outline'):
|
||||
prompt_parts.append(f"""## 📝 本章大纲
|
||||
|
||||
{project_context['chapter_outline']}
|
||||
|
||||
---
|
||||
""")
|
||||
|
||||
# 前置章节上下文
|
||||
if project_context.get('previous_context'):
|
||||
prompt_parts.append(f"""## 📚 前置章节上下文
|
||||
|
||||
{project_context['previous_context']}
|
||||
|
||||
---
|
||||
""")
|
||||
|
||||
# 写作风格要求
|
||||
if style_content:
|
||||
prompt_parts.append(f"""## 🎨 写作风格要求
|
||||
|
||||
{style_content}
|
||||
|
||||
请在重新创作时严格遵循上述写作风格。
|
||||
|
||||
---
|
||||
""")
|
||||
|
||||
# 创作要求
|
||||
prompt_parts.append(f"""## ✨ 创作要求
|
||||
|
||||
1. **解决问题**:针对上述修改指令中提到的所有问题进行改进
|
||||
2. **保持连贯**:确保与前后章节的情节、人物、风格保持一致
|
||||
3. **提升质量**:在节奏、情感、描写等方面明显优于原版
|
||||
4. **保留精华**:保持原章节中优秀的部分和关键情节
|
||||
5. **字数控制**:目标字数约{target_word_count}字(可适当浮动±20%)
|
||||
{f'6. **风格一致**:严格按照上述写作风格进行创作' if style_content else ''}
|
||||
|
||||
---
|
||||
|
||||
## 🎬 开始创作
|
||||
|
||||
请现在开始创作改进后的新版本章节内容。
|
||||
|
||||
**重要提示**:
|
||||
- 直接输出章节正文内容,从故事内容开始写
|
||||
- **不要**输出章节标题(如"第X章"、"第X章:XXX"等)
|
||||
- **不要**输出任何额外的说明、注释或元数据
|
||||
- 只需要纯粹的故事正文内容
|
||||
|
||||
现在开始:
|
||||
""")
|
||||
|
||||
return "\n".join(prompt_parts)
|
||||
|
||||
@classmethod
|
||||
def get_inspiration_prompt(cls, step: str) -> Optional[Dict[str, str]]:
|
||||
"""获取灵感模式指定步骤的提示词"""
|
||||
return cls.INSPIRATION_PROMPTS.get(step)
|
||||
|
||||
@classmethod
|
||||
def get_inspiration_quick_complete_prompt(cls, existing: str) -> Dict[str, str]:
|
||||
"""获取灵感模式智能补全的提示词"""
|
||||
return {
|
||||
"system": cls.format_prompt(cls.INSPIRATION_QUICK_COMPLETE, existing=existing),
|
||||
"user": "请补全小说信息"
|
||||
}
|
||||
|
||||
@classmethod
|
||||
def get_mcp_tool_test_prompts(cls, plugin_name: str) -> Dict[str, str]:
|
||||
"""获取MCP工具测试的提示词"""
|
||||
return {
|
||||
"user": cls.format_prompt(cls.MCP_TOOL_TEST, plugin_name=plugin_name),
|
||||
"system": cls.MCP_TOOL_TEST_SYSTEM
|
||||
}
|
||||
# 创建全局提示词服务实例
|
||||
|
||||
# ========== 自定义提示词支持 ==========
|
||||
|
||||
@classmethod
|
||||
async def get_template_with_fallback(cls,
|
||||
template_key: str,
|
||||
user_id: str = None,
|
||||
db = None) -> str:
|
||||
"""
|
||||
获取提示词模板(优先用户自定义,支持降级)
|
||||
|
||||
Args:
|
||||
template_key: 模板键名
|
||||
user_id: 用户ID(可选,如果不提供则直接返回系统默认)
|
||||
db: 数据库会话(可选)
|
||||
|
||||
Returns:
|
||||
提示词模板内容
|
||||
"""
|
||||
# 如果没有提供user_id或db,直接返回系统默认
|
||||
if not user_id or not db:
|
||||
return getattr(cls, template_key, None)
|
||||
|
||||
# 尝试获取用户自定义模板
|
||||
return await cls.get_template(template_key, user_id, db)
|
||||
|
||||
@classmethod
|
||||
async def get_template(cls,
|
||||
template_key: str,
|
||||
user_id: str,
|
||||
db) -> str:
|
||||
"""
|
||||
获取提示词模板(优先用户自定义)
|
||||
|
||||
Args:
|
||||
template_key: 模板键名
|
||||
user_id: 用户ID
|
||||
db: 数据库会话
|
||||
|
||||
Returns:
|
||||
提示词模板内容
|
||||
"""
|
||||
from sqlalchemy import select
|
||||
from app.models.prompt_template import PromptTemplate
|
||||
from app.logger import get_logger
|
||||
|
||||
logger = get_logger(__name__)
|
||||
|
||||
# 1. 尝试从数据库获取用户自定义模板
|
||||
result = await db.execute(
|
||||
select(PromptTemplate).where(
|
||||
PromptTemplate.user_id == user_id,
|
||||
PromptTemplate.template_key == template_key,
|
||||
PromptTemplate.is_active == True
|
||||
)
|
||||
)
|
||||
custom_template = result.scalar_one_or_none()
|
||||
|
||||
if custom_template:
|
||||
logger.info(f"✅ 使用用户自定义提示词: user_id={user_id}, template_key={template_key}, template_name={custom_template.template_name}")
|
||||
return custom_template.template_content
|
||||
|
||||
# 2. 降级到系统默认模板
|
||||
logger.info(f"⚪ 使用系统默认提示词: user_id={user_id}, template_key={template_key} (未找到自定义模板)")
|
||||
return getattr(cls, template_key, None)
|
||||
|
||||
@classmethod
|
||||
def get_all_system_templates(cls) -> list:
|
||||
"""
|
||||
获取所有系统默认模板的信息
|
||||
|
||||
Returns:
|
||||
系统模板列表
|
||||
"""
|
||||
templates = []
|
||||
|
||||
# 定义所有模板及其元信息
|
||||
template_definitions = {
|
||||
"WORLD_BUILDING": {
|
||||
"name": "世界构建",
|
||||
"category": "世界构建",
|
||||
"description": "用于生成小说世界观设定,包括时间背景、地理位置、氛围基调和世界规则",
|
||||
"parameters": ["title", "theme", "genre"]
|
||||
},
|
||||
"CHARACTERS_BATCH_GENERATION": {
|
||||
"name": "批量角色生成",
|
||||
"category": "角色生成",
|
||||
"description": "批量生成多个角色和组织,建立角色关系网络",
|
||||
"parameters": ["count", "time_period", "location", "atmosphere", "rules", "theme", "genre", "requirements"]
|
||||
},
|
||||
"SINGLE_CHARACTER_GENERATION": {
|
||||
"name": "单个角色生成",
|
||||
"category": "角色生成",
|
||||
"description": "生成单个角色的详细设定",
|
||||
"parameters": ["project_context", "user_input"]
|
||||
},
|
||||
"SINGLE_ORGANIZATION_GENERATION": {
|
||||
"name": "组织生成",
|
||||
"category": "角色生成",
|
||||
"description": "生成组织/势力的详细设定",
|
||||
"parameters": ["project_context", "user_input"]
|
||||
},
|
||||
"COMPLETE_OUTLINE_GENERATION": {
|
||||
"name": "完整大纲生成",
|
||||
"category": "大纲生成",
|
||||
"description": "根据项目信息生成完整的章节大纲",
|
||||
"parameters": ["title", "theme", "genre", "chapter_count", "narrative_perspective", "target_words",
|
||||
"time_period", "location", "atmosphere", "rules", "characters_info", "requirements", "mcp_references"]
|
||||
},
|
||||
"OUTLINE_CONTINUE_GENERATION": {
|
||||
"name": "大纲续写",
|
||||
"category": "大纲生成",
|
||||
"description": "基于已有章节续写大纲",
|
||||
"parameters": ["title", "theme", "genre", "narrative_perspective", "chapter_count", "time_period",
|
||||
"location", "atmosphere", "rules", "characters_info", "current_chapter_count",
|
||||
"all_chapters_brief", "recent_plot", "memory_context", "mcp_references",
|
||||
"plot_stage_instruction", "start_chapter", "end_chapter", "story_direction", "requirements"]
|
||||
},
|
||||
"OUTLINE_GENERATION": {
|
||||
"name": "基础大纲生成",
|
||||
"category": "大纲生成",
|
||||
"description": "生成基础章节大纲框架",
|
||||
"parameters": ["genre", "theme", "target_words", "requirements"]
|
||||
},
|
||||
"OUTLINE_EXPANSION": {
|
||||
"name": "大纲展开",
|
||||
"category": "大纲生成",
|
||||
"description": "将单个大纲节点展开为多个章节",
|
||||
"parameters": ["title", "genre", "theme", "narrative_perspective", "time_period", "location",
|
||||
"atmosphere", "rules", "characters_info", "outline_order", "outline_title",
|
||||
"outline_content", "context_info", "strategy_instruction", "target_chapters",
|
||||
"scene_instruction", "scene_field"]
|
||||
},
|
||||
"CHAPTER_GENERATION": {
|
||||
"name": "章节创作",
|
||||
"category": "章节创作",
|
||||
"description": "根据大纲创作章节内容",
|
||||
"parameters": ["title", "theme", "genre", "narrative_perspective", "time_period", "location",
|
||||
"atmosphere", "rules", "characters_info", "outlines_context", "chapter_number",
|
||||
"chapter_title", "chapter_outline", "target_word_count", "max_word_count"]
|
||||
},
|
||||
"CHAPTER_GENERATION_WITH_CONTEXT": {
|
||||
"name": "章节创作(带上下文)",
|
||||
"category": "章节创作",
|
||||
"description": "基于前置章节内容创作新章节",
|
||||
"parameters": ["title", "theme", "genre", "narrative_perspective", "time_period", "location",
|
||||
"atmosphere", "rules", "characters_info", "outlines_context", "previous_content",
|
||||
"memory_context", "chapter_number", "chapter_title", "chapter_outline",
|
||||
"target_word_count", "max_word_count"]
|
||||
},
|
||||
"CHAPTER_REGENERATION_SYSTEM": {
|
||||
"name": "章节重写系统提示",
|
||||
"category": "章节重写",
|
||||
"description": "用于章节重写的系统提示词",
|
||||
"parameters": ["chapter_number", "title", "word_count", "content", "modification_instructions",
|
||||
"project_context", "style_content", "target_word_count"]
|
||||
},
|
||||
"AI_DENOISING": {
|
||||
"name": "AI去味",
|
||||
"category": "辅助功能",
|
||||
"description": "将AI生成的文本改写得更自然",
|
||||
"parameters": ["original_text"]
|
||||
},
|
||||
"PLOT_ANALYSIS": {
|
||||
"name": "情节分析",
|
||||
"category": "情节分析",
|
||||
"description": "深度分析章节的剧情、钩子、伏笔等",
|
||||
"parameters": ["chapter_number", "title", "content", "word_count"]
|
||||
},
|
||||
"PLOT_EXPANSION_SINGLE_BATCH": {
|
||||
"name": "大纲单批次展开",
|
||||
"category": "情节展开",
|
||||
"description": "将大纲节点展开为详细章节规划(单批次)",
|
||||
"parameters": ["project_title", "project_genre", "project_theme", "project_narrative_perspective",
|
||||
"project_world_time_period", "project_world_location", "project_world_atmosphere",
|
||||
"characters_info", "outline_order_index", "outline_title", "outline_content",
|
||||
"context_info", "strategy_instruction", "target_chapter_count", "scene_instruction", "scene_field"]
|
||||
},
|
||||
"PLOT_EXPANSION_MULTI_BATCH": {
|
||||
"name": "大纲分批展开",
|
||||
"category": "情节展开",
|
||||
"description": "将大纲节点展开为详细章节规划(分批)",
|
||||
"parameters": ["project_title", "project_genre", "project_theme", "project_narrative_perspective",
|
||||
"project_world_time_period", "project_world_location", "project_world_atmosphere",
|
||||
"characters_info", "outline_order_index", "outline_title", "outline_content",
|
||||
"context_info", "previous_context", "strategy_instruction", "start_index",
|
||||
"end_index", "target_chapter_count", "scene_instruction", "scene_field"]
|
||||
},
|
||||
"MCP_TOOL_TEST": {
|
||||
"name": "MCP工具测试",
|
||||
"category": "MCP测试",
|
||||
"description": "用于测试MCP插件功能",
|
||||
"parameters": ["plugin_name"]
|
||||
},
|
||||
"MCP_WORLD_BUILDING_PLANNING": {
|
||||
"name": "MCP世界观规划",
|
||||
"category": "MCP增强",
|
||||
"description": "使用MCP工具搜索资料辅助世界观设计",
|
||||
"parameters": ["title", "genre", "theme", "description"]
|
||||
},
|
||||
"MCP_CHARACTER_PLANNING": {
|
||||
"name": "MCP角色规划",
|
||||
"category": "MCP增强",
|
||||
"description": "使用MCP工具搜索资料辅助角色设计",
|
||||
"parameters": ["title", "genre", "theme", "time_period", "location"]
|
||||
}
|
||||
}
|
||||
|
||||
for key, info in template_definitions.items():
|
||||
template_content = getattr(cls, key, None)
|
||||
if template_content:
|
||||
templates.append({
|
||||
"template_key": key,
|
||||
"template_name": info["name"],
|
||||
"category": info["category"],
|
||||
"description": info["description"],
|
||||
"parameters": info["parameters"],
|
||||
"content": template_content
|
||||
})
|
||||
|
||||
return templates
|
||||
|
||||
@classmethod
|
||||
def get_system_template_info(cls, template_key: str) -> dict:
|
||||
"""
|
||||
获取指定系统模板的信息
|
||||
|
||||
Args:
|
||||
template_key: 模板键名
|
||||
|
||||
Returns:
|
||||
模板信息字典
|
||||
"""
|
||||
all_templates = cls.get_all_system_templates()
|
||||
for template in all_templates:
|
||||
if template["template_key"] == template_key:
|
||||
return template
|
||||
return None
|
||||
prompt_service = PromptService()
|
||||
Reference in New Issue
Block a user