核心修复: - 修复PackageDiscovery._isValidDevelopmentRoot()检查resource目录而非prompt - 更新package.json files字段从prompt/改为resource/ - 修复RegisterCommand.js中的资源路径引用 - 更新WelcomeCommand.js中的@package://prompt/为@package://resource/ - 修复PromptProtocol.js中所有@package://prompt/路径引用 - 更新PackageProtocol.js示例路径 - 批量更新docs/目录下26个文档的路径引用 技术价值: - 解决PackageDiscovery无法加载系统级角色的问题 - 消除PackageProtocol的Access denied错误 - 实现prompt→resource语义重构的100%完整性 - 确保所有8个系统级角色正常加载和激活 验证结果: - ✅ 61个系统级资源正常加载 - ✅ 8个角色完全可用(assistant,frontend-developer,java-backend-developer,noface,nuwa,sean,xiaohongshu-marketer,product-manager) - ✅ welcome和action命令完全正常工作 🤖 Generated with [Claude Code](https://claude.ai/code) Co-Authored-By: Claude <noreply@anthropic.com>
235 lines
6.6 KiB
Markdown
235 lines
6.6 KiB
Markdown
# 角色内容解析不完整问题
|
||
|
||
## 🔥 问题等级
|
||
**高优先级 (High Priority)**
|
||
|
||
## 📋 问题描述
|
||
|
||
当前PromptX的角色解析机制存在重大缺陷:**只解析@引用,完全忽略DPML标签内的直接内容**。这导致许多用户自定义角色的核心能力丢失。
|
||
|
||
## 🔍 问题详情
|
||
|
||
### 当前解析机制
|
||
ActionCommand在`analyzeRoleDependencies`方法中使用以下正则表达式:
|
||
```javascript
|
||
const resourceRegex = /@([!?]?)([a-zA-Z][a-zA-Z0-9_-]*):\/\/([a-zA-Z0-9_\/.,-]+?)(?=[\s\)\],]|$)/g
|
||
```
|
||
|
||
这个正则**只提取@引用**,完全忽略DPML标签内直接编写的内容。
|
||
|
||
### 影响的角色类型
|
||
|
||
#### 1. 系统角色(使用@引用)
|
||
```xml
|
||
<!-- resource/domain/assistant/assistant.role.md -->
|
||
<role>
|
||
<personality>
|
||
@!thought://remember
|
||
@!thought://recall
|
||
@!thought://assistant
|
||
</personality>
|
||
<principle>
|
||
@!execution://assistant
|
||
</principle>
|
||
</role>
|
||
```
|
||
**状态**:✅ 正常解析
|
||
|
||
#### 2. 用户角色(直接内容)
|
||
```xml
|
||
<!-- .promptx/resource/domain/internet-debater/internet-debater.role.md -->
|
||
<role>
|
||
<personality>
|
||
# 网络杠精思维模式
|
||
## 核心思维特征
|
||
- **挑刺思维**:看到任何观点都先找问题和漏洞
|
||
- **抬杠本能**:天生反对派,习惯性质疑一切表述
|
||
...
|
||
</personality>
|
||
<principle>
|
||
# 网络杠精行为原则
|
||
## 核心抬杠准则
|
||
- **逢言必反**:对任何观点都要找到反对的角度
|
||
...
|
||
</principle>
|
||
<knowledge>
|
||
# 网络杠精专业知识体系
|
||
## 逻辑谬误大全
|
||
- **稻草人谬误**:故意曲解对方观点
|
||
...
|
||
</knowledge>
|
||
</role>
|
||
```
|
||
**状态**:❌ **内容完全丢失**
|
||
|
||
## 🎯 具体影响
|
||
|
||
### internet-debater角色损失分析
|
||
- **丢失内容**:3个完整的DPML节段,约100行专业内容
|
||
- **丢失能力**:
|
||
- 杠精思维模式和认知特征
|
||
- 抬杠行为原则和语言风格
|
||
- 逻辑谬误知识和争论技巧
|
||
- **用户体验**:激活角色后获得的是"空壳",无法发挥预期作用
|
||
|
||
### 潜在影响范围
|
||
- 所有直接编写内容的用户自定义角色
|
||
- 混合编写方式的角色(@引用 + 直接内容)
|
||
- 未来可能创建的角色
|
||
|
||
## 🔍 根因分析
|
||
|
||
### 1. 设计假设错误
|
||
系统设计时假设所有角色都使用@引用方式,但实际上:
|
||
- 用户更倾向于直接编写内容
|
||
- 文档没有强制要求使用@引用
|
||
- 角色创建工具支持直接编写
|
||
|
||
### 2. 验证与解析分离
|
||
```javascript
|
||
// resourceManager.js - 只验证格式,不解析内容
|
||
validateDPMLFormat(content, type) {
|
||
const tags = DPML_TAGS[type]
|
||
return content.includes(tags.start) && content.includes(tags.end)
|
||
}
|
||
```
|
||
|
||
### 3. 解析逻辑单一
|
||
ActionCommand只有一种解析模式:正则匹配@引用,没有考虑直接内容。
|
||
|
||
## 💡 解决方案
|
||
|
||
### 方案1:混合解析机制(推荐)
|
||
扩展ActionCommand解析逻辑,同时支持:
|
||
1. **@引用解析**:保持现有逻辑
|
||
2. **直接内容解析**:提取DPML标签内的Markdown内容
|
||
3. **内容合并**:@引用内容 + 直接内容 = 完整角色能力
|
||
|
||
### 方案2:内容提取器
|
||
创建专门的DPML内容提取器:
|
||
```javascript
|
||
class DPMLContentExtractor {
|
||
extractTagContent(content, tagName) {
|
||
const regex = new RegExp(`<${tagName}>([\\s\\S]*?)</${tagName}>`, 'g')
|
||
// 提取标签内容,同时处理@引用和直接内容
|
||
}
|
||
}
|
||
```
|
||
|
||
### 方案3:解析策略统一
|
||
统一角色解析策略:
|
||
1. 优先解析@引用
|
||
2. 补充解析直接内容
|
||
3. 合并生成完整的角色Profile
|
||
|
||
## 🔧 技术实现要点
|
||
|
||
### 1. 扩展依赖分析
|
||
```javascript
|
||
// ActionCommand.js
|
||
async analyzeRoleDependencies(roleInfo) {
|
||
const roleContent = await fs.readFile(filePath, 'utf-8')
|
||
|
||
// 现有:提取@引用
|
||
const references = this.extractReferences(roleContent)
|
||
|
||
// 新增:提取直接内容
|
||
const directContent = this.extractDirectContent(roleContent)
|
||
|
||
// 合并依赖
|
||
return this.mergeDependencies(references, directContent)
|
||
}
|
||
```
|
||
|
||
### 2. 内容提取算法
|
||
```javascript
|
||
extractDirectContent(content) {
|
||
const sections = {}
|
||
const tags = ['personality', 'principle', 'knowledge']
|
||
|
||
tags.forEach(tag => {
|
||
const regex = new RegExp(`<${tag}>([\\s\\S]*?)</${tag}>`, 'g')
|
||
const match = regex.exec(content)
|
||
if (match && match[1].trim()) {
|
||
// 过滤掉@引用,只保留直接内容
|
||
const directText = this.filterOutReferences(match[1])
|
||
if (directText.trim()) {
|
||
sections[tag] = directText
|
||
}
|
||
}
|
||
})
|
||
|
||
return sections
|
||
}
|
||
```
|
||
|
||
## 📊 影响评估
|
||
|
||
### 修复收益
|
||
- **功能完整性**:用户自定义角色能力完全恢复
|
||
- **用户体验**:角色激活后获得预期的专业能力
|
||
- **兼容性**:支持所有编写方式,向下兼容
|
||
|
||
### 修复成本
|
||
- **开发工作量**:中等(主要在ActionCommand和相关解析逻辑)
|
||
- **测试工作量**:中等(需要测试各种角色格式)
|
||
- **风险评估**:低(主要是增强功能,不破坏现有逻辑)
|
||
|
||
## 🧪 测试用例
|
||
|
||
### 测试场景1:纯@引用角色
|
||
```xml
|
||
<role>
|
||
<personality>@!thought://assistant</personality>
|
||
<principle>@!execution://assistant</principle>
|
||
</role>
|
||
```
|
||
**期望**:正常解析@引用
|
||
|
||
### 测试场景2:纯直接内容角色
|
||
```xml
|
||
<role>
|
||
<personality># 直接编写的个性内容</personality>
|
||
<principle># 直接编写的原则内容</principle>
|
||
</role>
|
||
```
|
||
**期望**:正确提取直接内容
|
||
|
||
### 测试场景3:混合方式角色
|
||
```xml
|
||
<role>
|
||
<personality>
|
||
@!thought://base-personality
|
||
|
||
# 补充的个性特征
|
||
- 额外特征1
|
||
- 额外特征2
|
||
</personality>
|
||
</role>
|
||
```
|
||
**期望**:@引用 + 直接内容都被解析
|
||
|
||
## 📅 建议修复时间线
|
||
- **阶段1**:问题确认和方案设计(已完成)
|
||
- **阶段2**:核心解析逻辑实现(1-2天)
|
||
- **阶段3**:测试用例编写和验证(1天)
|
||
- **阶段4**:兼容性测试和文档更新(1天)
|
||
|
||
## 🔗 相关文件
|
||
- `src/lib/core/pouch/commands/ActionCommand.js` - 主要修改文件
|
||
- `src/lib/core/resource/resourceManager.js` - 可能需要增强DPML处理
|
||
- `.promptx/resource/domain/internet-debater/internet-debater.role.md` - 受影响的测试案例
|
||
- `src/tests/commands/ActionCommand.*.test.js` - 需要补充的测试
|
||
|
||
## ⚠️ 注意事项
|
||
1. **保持向下兼容**:现有@引用方式不能受影响
|
||
2. **性能考虑**:内容解析不应显著影响角色激活速度
|
||
3. **内容去重**:避免@引用和直接内容的重复
|
||
4. **错误处理**:DPML格式错误时的优雅降级
|
||
|
||
---
|
||
|
||
**报告人**:Claude Code
|
||
**发现时间**:2025-06-11
|
||
**优先级**:High
|
||
**标签**:bug, role-parsing, user-experience, content-loss |