SillyTavern宏功能:可编程对话操作指南
引言:为什么需要宏功能?
在AI对话前端开发中,我们经常遇到重复性操作、动态内容生成和复杂逻辑处理的需求。SillyTavern的宏系统(Macro System)正是为了解决这些问题而设计的强大工具。通过宏功能,你可以实现:
- 动态内容替换和条件渲染
- 随机选择和概率控制
- 时间相关的智能处理
- 对话状态感知和上下文操作
- 自定义函数扩展
本文将深入解析SillyTavern宏系统的核心机制、内置宏功能,以及如何创建和使用自定义宏。
宏系统架构解析
核心类:MacrosParser
SillyTavern的宏功能基于MacrosParser类实现,这是一个静态类,负责宏的注册、管理和执行:
export class MacrosParser {
static #macros = new Map(); // 宏名称到值的映射
static #descriptions = new Map(); // 宏描述信息
// 注册全局宏
static registerMacro(key, value, description = '') {
// 参数验证和注册逻辑
}
// 取消注册宏
static unregisterMacro(key) {
// 清理逻辑
}
// 填充环境变量
static populateEnv(env) {
// 将注册的宏添加到环境对象
}
}
宏执行流程
内置宏功能详解
1. 基础替换宏
| 宏语法 | 功能描述 | 示例输出 |
|---|---|---|
{{newline}} | 插入换行符 | \n |
{{trim}} | 移除周围空白 | 空字符串 |
{{noop}} | 无操作占位符 | 空字符串 |
{{input}} | 获取当前输入框内容 | 用户输入文本 |
2. 消息上下文宏
// 获取最后一条消息
function getLastMessage() {
const mid = getLastMessageId();
return chat[mid]?.mes ?? '';
}
// 获取用户最后消息
function getLastUserMessage() {
const mid = getLastMessageId({ filter: m => m.is_user && !m.is_system });
return chat[mid]?.mes ?? '';
}
相关宏:
{{lastMessage}}- 最后一条消息内容{{lastUserMessage}}- 用户最后消息{{lastCharMessage}}- 角色最后消息{{lastMessageId}}- 最后消息ID
3. 时间处理宏
SillyTavern使用Moment.js进行时间处理,支持丰富的时间格式:
| 宏语法 | 输出格式 | 示例 |
|---|---|---|
{{time}} | 本地时间 | 3:45 PM |
{{date}} | 本地日期 | September 4, 2025 |
{{isotime}} | ISO时间 | 15:45 |
{{isodate}} | ISO日期 | 2025-09-04 |
{{weekday}} | 星期几 | Thursday |
自定义时间格式:
{{datetimeformat YYYY-MM-DD HH:mm:ss}} // 输出: 2025-09-04 15:45:30
4. 随机选择宏
简单随机选择
{{random::选项1::选项2::选项3}}
{{random 选项A,选项B,选项C}}
确定性选择(基于聊天ID哈希)
{{pick::选项1::选项2::选项3}} // 每次聊天会话中固定选择
实现原理:
function getPickReplaceMacro(rawContent) {
const chatIdHash = getChatIdHash();
const rawContentHash = getStringHash(rawContent);
// 基于聊天ID和内容哈希生成确定性随机数
}
5. 骰子滚动宏
支持标准的骰子表达式语法:
{{roll 2d6+3}} // 滚动2个6面骰子并加3
{{roll 1d20}} // 滚动1个20面骰子
{{roll 4d10}} // 滚动4个10面骰子
6. 高级功能宏
时间差计算
{{timeDiff::2025-09-04 15:00::2025-09-04 14:30}} // 输出: 30 minutes
字符串反转
{{reverse:Hello World}} // 输出: dlroW olleH
注释功能
{{// 这是注释内容,不会被渲染}}
自定义宏开发指南
1. 注册简单值宏
// 注册静态值宏
MacrosParser.registerMacro('version', '1.0.0', '当前系统版本');
// 注册函数宏
MacrosParser.registerMacro('randomNumber', () => {
return Math.floor(Math.random() * 100);
}, '生成0-99的随机数');
2. 创建上下文感知宏
// 基于聊天状态的宏
MacrosParser.registerMacro('chatLength', () => {
return chat?.length ?? 0;
}, '当前聊天消息数量');
// 基于用户身份的宏
MacrosParser.registerMacro('userRole', () => {
return isMobile() ? 'mobile_user' : 'desktop_user';
}, '用户设备类型');
3. 异步宏处理
虽然宏系统主要支持同步操作,但可以通过事件机制实现异步效果:
let lastGenerationType = '';
MacrosParser.registerMacro('lastGenerationType', () => lastGenerationType);
// 监听生成事件
eventSource.on(event_types.GENERATION_STARTED, (type, _params, isDryRun) => {
if (isDryRun) return;
lastGenerationType = type || 'normal';
});
实战应用场景
场景1:动态角色对话
// 在角色设定中使用宏
const characterConfig = {
greeting: "你好!{{random::今天天气真不错::刚刚看到有趣的事情}},{{time}}好!"
};
// 输出可能为: "你好!今天天气真不错,3:45 PM好!"
场景2:游戏化对话系统
// 骰子检定系统
const checkMessage = "进行敏捷检定: {{roll 1d20}},需要超过15才能成功";
// 条件对话分支
const branchDialog = `
{{if {{roll 1d20}} > 15}}
检定成功!你灵活地躲过了陷阱。
{{else}}
检定失败!你触发了机关。
{{endif}}
`;
场景3:智能时间响应
// 基于时间的问候语
const timeBasedGreeting = `
{{if {{isotime}} < "12:00"}}
早上好!{{user}},今天过得怎么样?
{{else if {{isotime}} < "18:00"}}
下午好!{{user}},工作还顺利吗?
{{else}}
晚上好!{{user}},休息时间到了。
{{endif}}
`;
最佳实践和注意事项
1. 性能优化
- 避免在宏中执行复杂计算
- 使用缓存机制存储重复使用的值
- 合理使用确定性随机(pick)而非完全随机
2. 错误处理
try {
content = content.replace(macro.regex, (...args) => {
return postProcessFn(macro.replace(...args));
});
} catch (e) {
console.warn(`宏替换失败: ${macro.regex}`, e);
}
3. 安全性考虑
- 验证用户输入的宏参数
- 避免执行任意代码
- 使用合适的转义和过滤
调试和测试技巧
1. 宏调试输出
// 在浏览器控制台中测试宏
const testContent = "测试: {{time}} {{random::A::B::C}}";
const result = evaluateMacros(testContent, {});
console.log("宏结果:", result);
2. 宏依赖检查
// 检查已注册的宏
for (const [key, description] of MacrosParser.#descriptions) {
console.log(`宏: ${key} - ${description}`);
}
总结
SillyTavern的宏系统提供了一个强大而灵活的可编程对话操作框架。通过内置的丰富宏功能和自定义扩展能力,开发者可以:
- 实现动态内容生成 - 基于时间、上下文和随机因素
- 创建智能对话流 - 条件分支和状态感知
- 构建游戏化体验 - 骰子机制和概率控制
- 扩展自定义功能 - 通过注册新的宏函数
掌握宏功能的使用,将极大提升你在SillyTavern中创建复杂、动态对话体验的能力。无论是简单的文本替换还是复杂的逻辑处理,宏系统都能提供优雅的解决方案。
记住:良好的宏使用应该保持简洁、高效,并且具有良好的错误处理。合理运用宏功能,让你的对话系统更加智能和生动!
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考



