df657e5e5af1a7a7ec9611156c80749b6bf5aa91
5
Commits
| Author | SHA1 | Message | Date | |
|---|---|---|---|---|
|
|
9a66068c33 |
v62:纪念日列表修正 / 分类图标与设置菜单 / 首页卡片体系
- 纪念日列表:display:flex 从 td 移到内层 div(写在 td 上会破坏表格列算法, 表现为关联人列与其它列高度不一致);行内列序按表头对齐; 改完再点「新建」不再带出上次修改的数据;文案改为「与我相关」「来自名册」; 别人记的、把我挂成关联人的条目一并显示(split() 返回 hiddenIds, 路由层据此过滤「接下来的日子」,与两张表同一套可见性) - 分类图标:新增 app/AnnivIcon.php(17 个行内 SVG 图标 + 同 key 的 emoji 供日历纯文本处使用,内网无 CDN 不用 FontAwesome);去掉「看日历」按钮; 设置按钮改为菜单,第一项进 days/settings 独立页;分类可自选图标, 列表徽标与日历条目都按分类显示 - 首页卡片:新增 app/HomeCards.php 与 templates/home_cards.php; 8 格宽 × 高 2/4/6/8;首页拆成 templates/home/_card_*.php 共 8 个片段; home/cards 可改尺寸、调顺序、开关 |
||
|
|
26026c7250 |
v53:纪念日记年份算「第几个」/ 首页待办排在进行中下面 / 日程编辑浮层跨满整行 / 新增成员打标签 / 新增页一次填完称呼与备注
用户 2026-10-16 五条。
① 纪念日要记录年份,才能知道「第几个」
用户原话:「纪念日需要记录年份,这样才能知道**是第几个纪念日**。」
**真根因有两层**(两处一起才构成"没有年份"):
· 表里没有:anniversaries 只有 month + day(当年当成"一年一度,年份无意义");
· 表单有、但被丢掉:日期控件本来就带年份(<input type="date"> 是 YYYY-MM-DD),
而拆分 JS **只取 mm/dd**(`mo.value = m[2]; dy.value = m[3];`)⇒ 想存也没存上。
修法:anniversaries.year(SMALLINT UNSIGNED NULL)+ 升级路径 addColumn;
表单补 hidden year、拆分 JS 一并写;Anniversary::save 收 year(**区间守卫 1900..2100**);
occurrences() 输出 year 与 nth;列表页显示「2018 年起 · 第 9 个」。
⚠️ 年份**可空、且不给默认值**:老数据就是没有年份,猜一个(按创建年之类)
会让页面算出一个**错的**"第 N 个"。NULL = 只按月日过、不显示序号 —— 诚实。
⚠️ 顺带修一个自相矛盾:repeat_type='once' 原来落在公历分支 ⇒ **年年都冒出来**;
现在有年份了 ⇒ 只在那一年出现(没年份的保持老行为,不凭空丢)。
🔴 **序号算法抽成单点来源 `Anniversary::nthFor()`** —— `occurrences()`(临近区)与
days/index.php(我添加的那张表)**都调它**;两处各写一遍是"改一处忘一处"的温床。
用**今天所在的年**("今年是第几个"),不是"下一次发生那年"。
🔴🔴 **踩坑(最值钱)**:`addColumn`(ALTER TABLE)**必须排在那张表 CREATE TABLE 之后**。
第一版放进 movie_details 那段(anniversaries 的建表更靠后)⇒ 全新安装
`1146 Table 'fb_test.anniversaries' doesn't exist` ⇒ 整段 ensure() 抛异常 ⇒
**install 直接"安装失败"**(POST 回 200、不自删、schema_version=None、库一片空白)。
新建库走 CREATE TABLE、老库走 addColumn —— **两条路都要在**。
② 首页近期任务:把待办也放进来(排在进行中下面)
用户原话:「首页的近期任务,**把待办也放进来吧,放在进行中的下面**。」
原来只收「进行中 + **已逾期**的待办」(当年怕待办一多首页变长清单)。
⇒ 现在**全部**收进来、按**状态分组**(doing 在前、todo 在后);
两组内部仍按截止时间升序(byStatus 的 ORDER BY 已排好)。
⚠️ 配套改统计:`count($tasks) 件在做` 会把待办也算成"在做" ⇒ 改成**按状态拆开数**
(进行中→「件在做」、待办→「件待办」,两数相加=列表行数,仍同源)。
「件待办」原读 stat7['todos'](**与列表不同源**,v24 踩过"数字和列表对不上")。
⚠️ 空态:「没有进行中的任务,也没有待办。」
⚠️ .hd-pane-body 本来就是 overflow-y:auto + flex:1 1 auto/min-height:0,行数变多**内部滚动**、
卡片高度不变(v32"两块外框恒等高"那套兜住了)。
③ 日程编辑浮层「只有左侧有内容,右侧空白,好像分栏了」
**真根因**(assets/css/app.css):日程编辑页 event.php 里,`.mv-grid`(观影式**纵向**列表)
被嵌在**两列**的 `.form-grid` 里 ⇒ 它只占**第一列**。整页形态下看不出来(页面宽),
但**浮层里面板只有 620px** ⇒ 两列各 286px ⇒ 所有字段挤在左边 286px、右边整列空着。
实测:panel=620 / form-grid=588 / cols="286px 286px" / mv-grid w=286
→修后 mv-grid w=588(95% of panel)、标题输入框 w=516、距右缘 ~2px。
修法:`.form-grid > .mv-grid { grid-column: 1 / -1; }` —— **一行 CSS**。
⚠️ 不去改 event.php 里"整页保留两列、浮层用 mv-grid"那个结构判断(那是有意保留的);
`.mv-grid` 本身就是"一整块、占满宽度"的语义,天生不该被塞进半列。
⚠️ 排查手法:这种"看起来像分栏"的问题**量几何比读 CSS 快** ——
getBoundingClientRect 打出 panel/grid/cols/内层宽,一眼看出"嵌了几层 grid"。
④ 添加成员时是**打标签**,不是选分组
用户原话:「名册中添加成员时,**不是选择分组,而是打标签**。现在已经没有分组的概念了,
**只有标签的概念**。」
⇒ 新增分支的「所属分组」下拉(group_id)换成**标签输入**(复用 v51 的 #ptBlock 那套:
候选勾选 + 自由输入,**文本框是唯一提交源**)。
⚠️ 只在**新增**时出现在那个位置(编辑时上面那个 #ptBlock 已在管标签,出现两块会让人以为填两遍)。
⚠️ **分组表结构 person_roster.group_id 保留不动**(名册"拖动归档"还在用、历史数据也在),
只是**新增入口不再要求人选**。
⚠️ e2e 里 v14「新增表单**有**分组下拉」与新需求正相反 ⇒ 改成「没有 group_id + 有 name=tags」。
⑤ 添加成员页一次填完「我对他的称呼 + 我的备注」
用户原话:「我在添加一个成员的时候,是不是可以直接在添加成员的页面里填写**我对他的称呼**
以及**我对他的备注**,**一次就解决**?要不然还得先添加、再返回他的名册去填,有点麻烦。」
⇒ 新增页也出现这两栏:
· **我对他的备注**(person_notes)—— 条件从 `$isEdit && !$isSelf` 改成 `!$isSelf`;
· **我对他的称呼**(nicknames)—— **新加的输入框** `name="my_nick"`。
服务端 people/create 落两表(挂**我**名下:viewer=我, target=他)。
⚠️ 判"表单里有没有这一栏"用 **array_key_exists**(不是判值是否为空)——
与编辑路径同一口径:**空串是明确的"清空"语义**(Nickname::set('') 会删行)。
⚠️ 四处**重渲染路径**(撞名确认/校验失败/手机号重复/people/new 初始)都要带上
myTags/tagChoices/myNick,否则一撞名或一报错,刚打的标签与刚写的称呼备注就全没了。
⚠️ 编辑页也补 myNick 回显(否则"新增时填了、编辑页看不见"会以为没存上)。
验证(新增 2 套件 + 更新 e2e/deploy 断言):
· _fb_v53_ui.py(**26 条**真机断言)
· _b53_falsify.py(**10 注入 / 10 全抓**,基线 26/0)
· e2e **1517/0**;familybook_deploy.sh 加 v53 静态断言段(14 正向 + 1 反向)
· 全流水线 **PUSH_RC=0**、部署 0 FAIL(含"第53批形态")
· 线上 8 文件 md5 逐字节一致;`anniversaries.year` 已由升级路径补上(nullable smallint);
线上实测 nthFor 4 用例全对(2018→第9个 / null→NULL / 2019→2 / 未来年→NULL);
诊断页已删并复验 404
⚠️ 本轮踩坑(已写进 pitfalls.md / 工作日志):
· **`addColumn` 必须在同表的 CREATE TABLE 之后**(否则全新安装 `1146` ⇒ ensure() 抛异常);
· **探针里 `dispatchEvent(new Event('submit'))` 不会真的提交表单**
(不导航、不发请求)⇒ 判"存没存上"必须真点提交按钮或 `requestSubmit()`;
· **反向验证的 `restore()` 不能只是"再跑一遍 build_work()"**(指纹闸门会把它变空操作
⇒ 第二轮基线是脏的,26/0 掉到 14/12);恢复必须**无条件** copy2;
· **注入锚点在源码里出现两次 ⇒ 打到别处 ⇒ 那条断言恒不红**
(v53 给新增页也加了 `id="ptBlock"`,打偏了 v51 那条"编辑页标签块"的注入);
· **别把两个共用 fb_test 库的套件并行跑**(互相删播种行 ⇒ 看着像"整套功能坏了");
· **部署静态断言的锚点引号/反斜杠必须与源码一字不差**:`\[` 在 bash 双引号里是
**字面反斜杠**、单双引号不能混、漏个 `(int)` 也搜不到 —— 一轮里连红 4 条全是这个。
|
||
|
|
a5e559b2b3 |
v25 第 25 批(9 条):名册分组不刷页 / 纪念日多人 / 首页等高 / 移出不回流 /
名册点击看详情拖动才排序 / 任务复选框与状态 / 财务标签多选 / 微信读书同步与统计 /
导航线上数据与图标
用户本轮 9 条需求(原话见 templates/ 与 app/ 内的逐条注释):
1. 名册:列表里给某人分组改为 AJAX 就地挪卡片(不再整页刷新)。
2. 纪念日:关联人改**多选**(复用 _person_picker,字段 person_ids[]);
自建纪念日的按钮与其它模块统一(改=蓝 .btn、删=黄 .btn-warn);
列表新增「关联人」列并给人名前加头像。
3. 首页:日程/任务两块**完全等高**(align-items:stretch + 固定总高 + flex 子项
min-height:0);修「0 件待办」——数字与右侧列表同源(原来各算各的)。
4. 🔴 名册里被移出的人过一阵又回来:根因是 PersonRoster::seedFromPersons()
**每次 Schema::ensure() 都无条件重灌**(线上实测每跑一次 +1 行)。
修:给它加自守卫(只有在 persons 还留着 group_id/sort_order 的**老库**才跑)。
5. 名册:点击=看详情、**只有拖 ⠿ 手柄**才是排序(原来整行既能点又能拖,语义混乱)。
6. 任务:所有任务前加复选框,任何位置点勾即完成;
状态语义照业界整理为 To Do / Doing / Done 并写出说明(用户要求参考别人的做法)。
7. 财务:类别标签改**多选非互斥**(再点一次取消该类别),上下两图 + 图例 + 表格
全部按同一个集合联动;高亮条刻意不给「合计」(多选下各类金额不能相加)。
8. 微信读书:新增**懒同步**(访问时顺手做,6h TTL,只补空字段不覆盖用户填的)、
封面图**拉下来存本站存储**(原来只存外链 → 看不到)、接官方 /readdata/detail 统计。
9. 导航:线上数据只搬了一半(5 板块 29 站 → 7 板块 67 站 + 67 图标)、
展示页头像不显示 / 搜索按钮错位 / 点登录 404。三个真根因:
· 相对地址在 /nav/ 下全 404 → 新增 Nav::abs();
· 搜索容器丢了 id="search"(CSS 是 #search button.submit 绝对定位);
· Nav::iconKey() 与 SimpleNav 的 icon_key() **算法不一致**(少一次 md5 归一化)
→ 搬来的图标文件名对不上;且 uploads/ 整目录 Require all denied。
新增两个**免登录公开出口** nav_icon.php / nav_avatar.php。
顺带修掉一个「数据损坏级」的真 bug(做第 4 条线上反证时发现的,之前一直没人注意):
app/Region.php 三处用中文标点当 trim/ltrim 的 charlist,而 PHP 的 charlist 是
**按字节**匹配的 —— 「。」= E3 80 **82** → 字节 82 进了可剥集合 →
「层」= E5 B1 **82** 被切掉尾字节 → 非法 UTF-8 → backfillAddress 的 UPDATE 报
`1366 Incorrect string value` → **地址拆分升级从上线起一直在失败被跳过**(每请求报一次)。
改成字符级 preg_replace('/…/u');线上实测 ensure() 现在无报错、待拆行数真的在下降。
验证战绩:
- e2e 1289/0(新增 Region 字节级用例等)
- 真机探针:选人 19/0 · 首页/导航 24/0 · 导航模块 34/0 · b18 暂存+确定 10/0 ·
第23批 52/0
- 桌面几何 428/0 · 移动端几何 680/0 · 交互 92/0 · 窄屏 24/0
- 老库升级 153/0(含 anniversary_people 迁移 + 「再跑 ensure() 名册行数不变」)
- 部署静态断言 180 OK / 0 FAIL · 反向验证 3/3 + Region 三变体各被两条断言同时抓住
- 线上 26 个文件与本地**逐字节一致**;展示页 200、图标 66/66 200、登录 200、
越权/不存在均 404、签发短语后 ensure() 不再报错。
|
||
|
|
e0562b8627 |
v24 第 5 轮:十条清单(天气填城市 / 输入即筛选 / 看板列=看板 / 账本盘点折线图 / 纪念日分类)
用户 2026-10-03 的十条,逐条落点: 1. 天气改为**个人设置里填城市**(每人一份):新增 app/Geo.php,内置 197 个 地级市坐标(离线、逐条核对,生成脚本 _tooling/_fb_geo_gen.py)。填坐标仍 作为内置表没有时的出口;老的家庭级坐标保留为兜底,升级当天天气不会凭空消失。 2. 所有"找个人"的地方**输入即筛选**:新增 assets/js/filter.js(纯前端显隐, 不发请求、回车不刷新)+ app/PersonQuery.php 把服务端判据收敛成一份 (名册 / 挑人 / 高级搜索共用,避免三处实现漂移)。 3. 名册列表:有昵称就不重复显示本名、行变矮、补齐手机/阴历阳历生日(带年份)/ 邮箱/工作单位;「清除」与「搜索」同款同尺寸。 4/5. 日程:撤掉左侧日历本栏改满宽,功能(显隐/颜色/导入/默认视图)全收进 右侧 ☰;**色块高度改为按起止时长**(旧实现一律 30 分钟,三小时的会跟 十五分钟的同高);点日历空白处即建日程,开始时间=点的那一格。 6/10. 资源:搜索提到最上;按"最近改动/最新新增"排序,默认只显示最新 10 条并 给「显示全部」出口。 7. 任务:看板的**列=用户自定义的看板**(不再是写死的待办/进行中), 拖动/左右键=换看板(改 board_id,不动 status)。 8. 财务:概览在上账目在下、记一笔改右侧按钮、账本设置(共享/改名/新建/删除) 收进 ☰、默认账本名「xxx的账本」、"挂在谁名下"默认自己且用标准选人框; **新增盘点**(新增 ledger_entry_snapshots 只增不改的历史表,旧值不被清空) + 上面画金额变化折线图(app/chart.php 服务端画 SVG,零依赖)。 9. 纪念日:手动添加的与名册生日派生的**分两块**、手动的在上;右侧设置可增删 分类(家庭级,删分类不强改已用的历史)。 本轮另外修掉/加固的四类问题(都由新增的静态或运行时守卫兜住): - index.php 少写 2 个 use 导入(Pinyin / UserSetting)→ 名册与个人设置 返回 200 但正文是 Fatal;顺带修了一处早已存在的 Attachment 未导入。 → 新增 _fb_import_check.py(1f 段)。 - 一次不精确替换弄丢了 app/Calendar.php 开头的 `<?php`,整份源码被当 HTML 吐给浏览器,而 `php -l` 报"无语法错误"(纯文本输出确实合法)。 → 新增 _fb_php_open_check.py(1e 段)。 - 模板片段 unset 了宿主模板的变量(账本片段 unset($canWrite))→ 正文里一片 Undefined variable 而 HTTP 仍 200。同 _datetime.php 早年 $t 的坑。 → 新增 _fb_fragment_scope_check.py(1g 段)+ _fb_batch_e.py 的 26 页无告警巡检。 - 窄屏下页头动作区不换行 → 周视图横向溢出且按钮被挤成三种高度(用户提过三次 "按钮要同高")→ .page-head .actions 加 flex-wrap。 验证战绩(全绿): e2e 773/0 · 第 5 轮专项 91/0 · 结构升级 126/0 · 几何 428/0 · 移动端 684/0 · 交互 97/0 · 家谱 26/0 · 按钮 60/0;三轮反向验证各 3/3 抓到,还原后复绿。 线上:schema v14、指纹一致(9df6c9fccc6796db)、snapshots 表已建、197 城、 8 个关键文件 md5 与本地逐字节一致、app/ 403 无源码泄漏、错误日志无新增。 |
||
|
|
8f80f3e835 |
v24 第 2 轮:19 条清单收尾(附件预览/CalDAV/任务分类看板/全局选人/家谱/纪念日/财务)
用户 2026-10-02 提的 19 条需求,本轮完成剩下的 8 条 + CalDAV 服务端:
- ③ 附件:图片/视频给缩略图,PDF/Word/Excel 给**同尺寸**图标;可预览的在本页
弹层里看(不再新开标签页),渲染不了的点了直接下载;预览层右上角恒有下载按钮。
- ⑦b CalDAV:把「我的日历本」按 RFC 4791 只读子集分享出去(OPTIONS/PROPFIND/
REPORT/GET,写方法一律 403)。用**专用口令**(库里只存 sha256),不是登录口令。
- ⑨⑩ 任务:分类与看板都由用户自建;已完成的任务从看板消失,改在「已完成」页
按分类查看/搜索;设置入口在「新建任务」旁的 ☰。
- ⑪ 全局人员选择器:一个片段铺到观影/旅程/资源/日历共享/任务共享/财务共享;
修掉了老组件「名字和拼音都搜不动」的 bug —— .att-item 自己声明了 display:flex,
压过了浏览器 [hidden]{display:none},过滤根本没生效。
- ⑫ 家谱:头像改方形不再裁切;姻亲不在图上的卡片给「⇄ 姻亲」入口,
以 TA 为中心重画 + 「返回我的家谱」。
- ⑬ 纪念日:阴历/阳历都能设且按对应历法重复;名册里每个人的生日默认可见
(实时派生,不复制一份);全部作为全天日程进日历。
- ⑮ 财务:账本可共享,双方都能记账、都能看全部账目,资产−负债=净资产;
金额一律以「分」存,不用浮点。
验证:端到端 724 项通过 / 0 失败;几何 368、交互 97、移动端 516、家谱 24、
升级 123 全绿;SQL 列名静态校验 0 处可疑;部署 11 条线上探针全过。
|