Files
writing-agent/src/preset/store.ts
T
chenmoranzhi f3303038fe 新增预设工作台:编辑、版本树、结构检查、用例试跑放在同一页。
改预设要能一边写一边看装出来的 messages,还要多模型对照,所以把编辑与试跑拆成两个视图塞进一个页面;版本存完整快照、可分叉,用例全局共用一份、运行记录按预设存。顺带让读预设文件先剥 BOM,静态资源改成不缓存,免得改了脚本还要强刷。
2026-10-26 01:09:40 +08:00

89 lines
2.7 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import { readdirSync, readFileSync, unlinkSync, writeFileSync } from "node:fs";
import path from "node:path";
import type { PresetPackage } from "../types/preset.js";
import { ensureUserDataDirs, getPresetsDir } from "../config/user-data-dir.js";
import { importSillyTavernPreset } from "./importer.js";
import { clearToolPlanCache } from "./tool-policy.js";
/** 旧预设里的思考强度不再使用;读到就从文件里删掉。 */
function withoutReasoningEffort(preset: PresetPackage, filePath: string): PresetPackage {
if (preset.generation?.reasoningEffort === undefined) return preset;
const generation = { ...preset.generation };
delete generation.reasoningEffort;
const next = { ...preset, generation };
writeFileSync(filePath, JSON.stringify(next, null, 2), "utf8");
return next;
}
function presetPath(id: string): string {
return path.join(getPresetsDir(), `${id}.json`);
}
/** Windows 编辑器可能给 JSON 加 BOM;JSON.parse 不认,先剥掉。 */
function parsePreset(raw: string): PresetPackage {
return JSON.parse(raw.replace(/^\uFEFF/, "")) as PresetPackage;
}
export function listPresets(): PresetPackage[] {
ensureUserDataDirs();
let files: string[];
try {
files = readdirSync(getPresetsDir()).filter((f) => f.endsWith(".json"));
} catch {
return [];
}
const presets: PresetPackage[] = [];
for (const file of files) {
try {
const filePath = path.join(getPresetsDir(), file);
const raw = readFileSync(filePath, "utf8");
presets.push(withoutReasoningEffort(parsePreset(raw), filePath));
} catch {
/* skip corrupt files */
}
}
return presets.sort((a, b) => a.name.localeCompare(b.name, "zh-CN"));
}
export function getPreset(id: string): PresetPackage | null {
try {
const filePath = presetPath(id);
const raw = readFileSync(filePath, "utf8");
return withoutReasoningEffort(parsePreset(raw), filePath);
} catch {
return null;
}
}
export function savePreset(preset: PresetPackage): PresetPackage {
ensureUserDataDirs();
writeFileSync(presetPath(preset.id), JSON.stringify(preset, null, 2), "utf8");
// 条目/内容被改过,导入时算好的工具映射要重建
clearToolPlanCache(preset.id);
return preset;
}
export function deletePreset(id: string): void {
clearToolPlanCache(id);
try {
unlinkSync(presetPath(id));
} catch {
/* ignore */
}
}
export function importAndSavePreset(
raw: unknown,
options: { name?: string } = {},
) {
const report = importSillyTavernPreset(raw, options);
savePreset(report.preset);
return report;
}
export function resolveActivePreset(activePresetId: string | null): PresetPackage | null {
if (!activePresetId) return null;
return getPreset(activePresetId);
}