feat(tui): 清单编辑器循环(第一轮第五块·装配完成)

装配:选行 → 选新方向 → 逐行校验 → 校验后原子保存 + 时间戳备份。输入走 -Driver,所以门禁里能用 -InputScript @('Enter','Down','Enter') 走完整流程,断言看返回值与**文件内容**,不需要捕获控制台输出。

四条"不猜":取消时什么都不写也不产生备份;方向菜单**预选当前值**(不预选的话"连按两次回车"会把字段改成菜单第一项 —— 不是没改,是改错了);方向没变直接返回"没有变化";保存前逐行校验(每行都要能被 ConvertFrom-BackupListLine 解析)—— 这正是 TUI 编辑器比手改安全的地方。

这个函数我试了两次才落地,两次都栽在同一件事上:**用脚本做多行字符串替换时,换行被折成空格**,于是注释与赋值落进同一行、被整段注释掉(症状是"对象没有属性"/"流程莫名走取消分支")。所以这条现在当硬约束执行:多行代码一律整份写文件,不做插入+删除式的拼接。

判据 12 条,覆盖保存 / 取消 / 无变化三条路径,并逐条断言注释行与未编辑行一字不动、备份里存原文、取消时不新增备份。

验收:test.ps1 9/9 全绿(5.1 与 7)。
This commit is contained in:
Shuery committed 2026-09-27 16:40:38 +08:00
1 parent e1fe99671b
commit 5df40d3341
4 files changed
+147

No files matched your search

+38
View File
@@ -1647,6 +1647,44 @@ Test-Case '改方向:只动行首标记,其余逐字节保持,且保留用
Assert-True $threw '注释行改方向必须抛错'
}
Test-Case '清单编辑器:脚本驱动走完"选行→改方向→保存",只动一行且留下备份' {
$dir = Join-Path $env:TEMP ("bnr-listed-" + [guid]::NewGuid().ToString('N').Substring(0, 8))
New-Item -ItemType Directory -Path $dir -Force | Out-Null
$file = Join-Path $dir 'BackupList.txt'
$utf8Bom = New-Object System.Text.UTF8Encoding($true)
$original = "# 注释一`nEdge`n+WindowsTerminal :encrypt`n"
[System.IO.File]::WriteAllText($file, $original, $utf8Bom)
$backupDir = Join-Path $dir 'logs\config-backups'
try {
# 1) 选第一行(回车)、方向菜单预选当前值 both、下移到 backup、回车应用
$r = Invoke-BakNRetBackupListEditor -Path $file -Driver (New-BakNRetInputDriver -Script @('Enter', 'Down', 'Enter'))
Assert-Equal $true $r.Saved '应当保存'
$after = @((Get-Content -LiteralPath $file -Raw -Encoding UTF8) -split "`r?`n")
Assert-Equal '# 注释一' $after[0] '注释行一字不动'
Assert-Equal '+Edge' $after[1] '第一行改成了 +Edge'
Assert-Equal '+WindowsTerminal :encrypt' $after[2] '第三行一字不动'
Assert-True (Test-Path $r.BackupPath) '应当留下时间戳备份'
Assert-Equal $original ([System.IO.File]::ReadAllText($r.BackupPath)) '备份里是原文'
# 2) 取消(Esc):什么都不写,也不产生新备份
$backupsBefore = @(Get-ChildItem $backupDir -File | Measure-Object).Count
$contentBefore = [System.IO.File]::ReadAllText($file)
$c = Invoke-BakNRetBackupListEditor -Path $file -Driver (New-BakNRetInputDriver -Script @('Esc'))
Assert-Equal $false $c.Saved '取消不该保存'
Assert-Equal $false $c.Changed '取消不该标记为已改'
Assert-Equal $contentBefore ([System.IO.File]::ReadAllText($file)) '取消后文件内容不变'
Assert-Equal $backupsBefore @(Get-ChildItem $backupDir -File | Measure-Object).Count '取消不该新增备份'
# 3) 方向没变:菜单预选当前值 backup,直接回车 → 说明"没有变化",不白写一次盘
$same = Invoke-BakNRetBackupListEditor -Path $file -Driver (New-BakNRetInputDriver -Script @('Enter', 'Enter'))
Assert-Equal $false $same.Saved '方向没变不该保存'
Assert-True ($same.Error -like '*没有变化*') '应当说明原因'
Assert-Equal $contentBefore ([System.IO.File]::ReadAllText($file)) '文件内容仍然不变'
} finally {
Remove-Item -LiteralPath $dir -Recurse -Force -ErrorAction SilentlyContinue
}
}
# ============================================================================
Remove-Item -LiteralPath $sandbox -Recurse -Force -ErrorAction SilentlyContinue
Remove-Item -LiteralPath $itemSandbox -Recurse -Force -ErrorAction SilentlyContinue