104 lines
3.9 KiB
Swift
104 lines
3.9 KiB
Swift
import Testing
|
|
@testable import 康康
|
|
|
|
/// 日记追问对话的 prompt 拼装契约:收尾/继续两种口径互斥、红线短语、
|
|
/// dataJSON 原文嵌入、蒸馏截断与 /no_think 结尾。
|
|
/// 对齐 DiaryOrganizePromptTests 风格:纯字符串断言,不涉隔离。
|
|
struct DiaryChatPromptTests {
|
|
|
|
/// 唯一、易断言的注入片段。
|
|
private let dataJSON = #"{"indicators":[{"name":"收缩压","value":"145"}]}"#
|
|
|
|
// MARK: 收尾口径(roundsLeft == 0)
|
|
|
|
@Test func replyAtZeroRoundsForbidsFurtherQuestions() {
|
|
let prompt = DiaryChatPrompts.reply(
|
|
transcript: "我: 我今天头疼",
|
|
latest: "我头疼",
|
|
dataJSON: dataJSON,
|
|
roundsLeft: 0
|
|
)
|
|
#expect(prompt.contains("不要再提任何问题"))
|
|
#expect(!prompt.contains("最多问 1 个新问题"))
|
|
}
|
|
|
|
// MARK: 继续口径(roundsLeft > 0)
|
|
|
|
@Test func replyWithRoundsLeftAllowsOneMoreQuestion() {
|
|
let prompt = DiaryChatPrompts.reply(
|
|
transcript: "我: 我今天头疼",
|
|
latest: "我头疼",
|
|
dataJSON: dataJSON,
|
|
roundsLeft: 2
|
|
)
|
|
#expect(prompt.contains("最多问 1 个新问题"))
|
|
#expect(!prompt.contains("不要再提任何问题"))
|
|
}
|
|
|
|
// MARK: 红线短语 + dataJSON 原文嵌入(opening 与 reply 都要有)
|
|
|
|
@Test func openingCarriesNoReferralRuleAndEmbedsDataJSON() {
|
|
let prompt = DiaryChatPrompts.opening(dataJSON: dataJSON)
|
|
#expect(prompt.contains("不写「建议就医」"))
|
|
#expect(prompt.contains(dataJSON))
|
|
}
|
|
|
|
@Test func replyCarriesNoReferralRuleAndEmbedsDataJSON() {
|
|
let prompt = DiaryChatPrompts.reply(
|
|
transcript: "我: 我今天头疼",
|
|
latest: "我头疼",
|
|
dataJSON: dataJSON,
|
|
roundsLeft: 1
|
|
)
|
|
#expect(prompt.contains("不写「建议就医」"))
|
|
#expect(prompt.contains(dataJSON))
|
|
}
|
|
|
|
// MARK: 蒸馏 prompt 的取材约束短语
|
|
|
|
@Test func distillContainsUserOnlyAndForbiddenRule() {
|
|
let prompt = DiaryChatPrompts.distill(transcript: "我: 我今天头疼\n康康: 收到")
|
|
#expect(prompt.contains("只取「我:」"))
|
|
#expect(prompt.contains("绝对不许"))
|
|
}
|
|
|
|
// MARK: 三个 prompt trim 后都以 /no_think 结尾
|
|
|
|
@Test func openingEndsWithNoThink() {
|
|
let prompt = DiaryChatPrompts.opening(dataJSON: dataJSON)
|
|
#expect(prompt.trimmingCharacters(in: .whitespacesAndNewlines).hasSuffix("/no_think"))
|
|
}
|
|
|
|
@Test func replyEndsWithNoThink() {
|
|
let prompt = DiaryChatPrompts.reply(
|
|
transcript: "我: 我今天头疼",
|
|
latest: "我头疼",
|
|
dataJSON: dataJSON,
|
|
roundsLeft: 1
|
|
)
|
|
#expect(prompt.trimmingCharacters(in: .whitespacesAndNewlines).hasSuffix("/no_think"))
|
|
}
|
|
|
|
@Test func distillEndsWithNoThink() {
|
|
let prompt = DiaryChatPrompts.distill(transcript: "我: 我今天头疼")
|
|
#expect(prompt.trimmingCharacters(in: .whitespacesAndNewlines).hasSuffix("/no_think"))
|
|
}
|
|
|
|
// MARK: 蒸馏对超长稿件截断到 distillTranscriptLimit(2000)
|
|
|
|
@Test func distillTruncatesTranscriptBeyondLimit() {
|
|
// 起始标记落在前 2000 内应保留;越限标记落在第 2500 字符附近应被截掉。
|
|
let earlyMark = "起始标记AAA"
|
|
let lateMark = "越限标记ZZZ"
|
|
let transcript = earlyMark
|
|
+ String(repeating: "文", count: 2500 - earlyMark.count) // 把越限标记推到 index≈2500
|
|
+ lateMark
|
|
+ String(repeating: "字", count: 500) // 凑到 3000+ 字符
|
|
#expect(transcript.count > DiaryChatPrompts.distillTranscriptLimit)
|
|
|
|
let prompt = DiaryChatPrompts.distill(transcript: transcript)
|
|
#expect(prompt.contains(earlyMark))
|
|
#expect(!prompt.contains(lateMark))
|
|
}
|
|
}
|