补全页:手工填过的值自动进下拉候选,后面同类地点不用再打一遍

下拉的候选是渲染时定好的,这一页手工新填的活动名/类别进不去候选,
后面遇到同类地点只能照着再敲一遍——这正是「其它(自己写)」最费事的地方。

现在填过的值会被记住并补进同类下拉,标成「新填:X」,插在建议之后、
真正的候选之前,一眼就能挑到;本页实时同步(打字即生效),
翻页和点「用高德分析」重载也留得住,提交成功后清掉(那之后它们已经是真候选了)。

顺带两处:
- 草稿保存改成按 name 合并,翻页不再把上一页填的覆盖掉;分页链接也接了保存。
- 重画候选前先把「这一格已经选中的新填值」留住再还回去,
  否则改一下文本框就会把别的行选好的值悄悄抹成空。

文本框的监听直接挂在框上而不是委托到 document:`new Event('input')` 默认不冒泡,
探针第一次就是这么假绿的——直接挂不依赖冒泡,也少一层隐式约定。
This commit is contained in:
tamakyi
2026-09-20 09:32:07 +08:00
parent bf23fc62d7
commit ffee082fad
2 changed files with 102 additions and 3 deletions
+21
View File
@@ -301,3 +301,24 @@ func TestFillupCustomActivityEmptyIsSkipped(t *testing.T) {
t.Fatalf("没填名字不该建类型,活动数 %d → %d", before, n)
}
}
// 「手工填过的值自动进候选」是纯前端行为,Go 测不到运行时,只能钉住它还在模板里。
// 这东西少一半都不会报错,只会悄悄退回「后面每行都得重新打一遍」——
// 所以把三个关键标记都钉住:存下来的键、注入选项的标记、显示用的前缀。
func TestFillupKeepsHandwrittenCandidates(t *testing.T) {
f := newMovementFixture(t)
fillupPlace(t, f)
rec := httptest.NewRecorder()
req := httptest.NewRequest("GET", "/admin/fillup", nil).WithContext(f.ctx)
f.srv.adminFillupPage(rec, req)
if rec.Code != http.StatusOK {
t.Fatalf("渲染失败: %d", rec.Code)
}
body := rec.Body.String()
for _, want := range []string{"rond-fillup-newopts", "data-local", "新填:"} {
if !strings.Contains(body, want) {
t.Errorf("模板里找不到 %q —— 「手工填过的值自动进候选」失效了", want)
}
}
}