端上编辑行程时图片视频带不全(服务端返回9个全部正常) #55

Open
opened 2026-11-05 04:42:52 +00:00 by laoyang · 2 comments
Owner

端上编辑行程时图片/视频带不全:服务端返回9个,端上只显示部分

现象

「修改编辑行程,图片和视频带进来都不全的问题。」

用户 2026-11-05 在网页端新增了图片和视频,行程列表里能看到,
但点「编辑」进去后带不全。

已排除(服务端全对)

用真实 token 打 GET /api/v1/trips/227/nodes:

HTTP 200  响应 4874 字节
节点数: 2
node #26  附件=9
    第一条键: id, family_id, target_type, target_id, key, name, mime, size,
              is_image, position, uploader_id, created_at, updated_at, deleted_at
    id/key/is_image: 120 / 'photos/be4af2e3300c2cfcea8a33c5.jpg' / 1
node #27  附件=0
  • Trip::nodes() 返回 9 个附件 ✅
  • key 无一为空 ✅
  • id / mime / is_image 字段齐全 ✅
  • attachsOf() 解析逻辑正确(逐条取 key,空则跳过)✅
  • this.photos = e.attachs 回填代码存在 ✅
  • 照片墙 ForEach(this.photos) 渲染代码存在 ✅

待定位

静态排查到此为止,服务端与端上代码都看不出问题。

疑点清单:

# 疑点 验证方法
1 editing 传的是旧对象(this.editNode 在 nodes 更新后没刷新) 加日志看 e.attachs.length
2 fbImageSrc 返回的 URL 无效 ⇒ 数据在但图不显示 检查 key 是否已是完整路径
3 if (this.photos.length > 0) 在 @Builder 里没触发重渲染 换成 ForEach 内判空
4 图片加载失败(网络/鉴权)但没有占位提示 加 onError 显示占位

本次改动(待验证)

① 加诊断日志(DIAG-ATTACH / DIAG-FILL),已随 86de596 提交
② 图片加载失败时显示灰色占位 + 文件名,不再"白块/看不见"

验收

  • 编辑有 9 个附件的行程,9 个全部显示
  • 图片加载失败时有明确占位(不是空白)
  • 视频缩略图有播放标记

备注

hdc shell 在本机被安全策略拦截,抓不到端上日志 ⇒ 只能靠"改代码 + 用户实测"闭环。
诊断日志保留在代码里,方便下次直接看 hilog。


为什么单独建单

#51 讲的是地址详细信息的 onPick 回调;本单是编辑时照片墙回填不全,属于附件链路。两者都在 FbTripNodeSheet 里但数据源不同。

# 端上编辑行程时图片/视频带不全:服务端返回9个,端上只显示部分 ## 现象 > 「修改编辑行程,图片和视频带进来都不全的问题。」 用户 2026-11-05 在网页端新增了图片和视频,行程**列表里能看到**, 但点「编辑」进去后**带不全**。 ## 已排除(服务端全对) 用真实 token 打 `GET /api/v1/trips/227/nodes`: ``` HTTP 200 响应 4874 字节 节点数: 2 node #26 附件=9 第一条键: id, family_id, target_type, target_id, key, name, mime, size, is_image, position, uploader_id, created_at, updated_at, deleted_at id/key/is_image: 120 / 'photos/be4af2e3300c2cfcea8a33c5.jpg' / 1 node #27 附件=0 ``` - `Trip::nodes()` 返回 9 个附件 ✅ - `key` 无一为空 ✅ - `id` / `mime` / `is_image` 字段齐全 ✅ - `attachsOf()` 解析逻辑正确(逐条取 key,空则跳过)✅ - `this.photos = e.attachs` 回填代码存在 ✅ - 照片墙 `ForEach(this.photos)` 渲染代码存在 ✅ ## 待定位 静态排查到此为止,服务端与端上代码**都看不出问题**。 疑点清单: | # | 疑点 | 验证方法 | |---|---|---| | 1 | `editing` 传的是**旧对象**(`this.editNode` 在 `nodes` 更新后没刷新) | 加日志看 `e.attachs.length` | | 2 | `fbImageSrc` 返回的 URL 无效 ⇒ 数据在但图不显示 | 检查 `key` 是否已是完整路径 | | 3 | `if (this.photos.length > 0)` 在 @Builder 里没触发重渲染 | 换成 ForEach 内判空 | | 4 | 图片加载失败(网络/鉴权)但**没有占位提示** | 加 `onError` 显示占位 | ## 本次改动(待验证) ① 加诊断日志(`DIAG-ATTACH` / `DIAG-FILL`),已随 `86de596` 提交 ② 图片加载失败时显示灰色占位 + 文件名,不再"白块/看不见" ## 验收 - [ ] 编辑有 9 个附件的行程,9 个全部显示 - [ ] 图片加载失败时有明确占位(不是空白) - [ ] 视频缩略图有播放标记 ## 备注 `hdc shell` 在本机被安全策略拦截,抓不到端上日志 ⇒ 只能靠"改代码 + 用户实测"闭环。 诊断日志保留在代码里,方便下次直接看 hilog。 --- ### 为什么单独建单 #51 讲的是地址详细信息的 onPick 回调;本单是编辑时照片墙回填不全,属于附件链路。两者都在 FbTripNodeSheet 里但数据源不同。
Author
Owner

2026-11-05 进展

已定位根因

@Param editing 在 ArkUI V2 里是单向同步:父组件改 editNode 后,
子组件的 editing 会更新,但 aboutToAppear 只在首次创建时跑一次。

⇒ 换一条行程再点编辑时,editing 变了但回填不重跑
⇒ this.photos 保留上一次的值(可能为空)⇒ 附件带不全。

这正是"列表里能看到、点编辑带不全"的原因:列表用的 nodes 数据是新的,
但浮层里的回填是上一次的。

修法

加一个重建序号:

@Local nodeSheetSeq: number = 0;

// 点编辑时
this.editNode = n;
this.nodeSheetSeq = this.nodeSheetSeq + 1;   // ← 序号 +1
this.nodeSheetTripId = this.tripId;

// 组件上
FbTripNodeSheet({ ... })
  .id('nodeSheet_' + this.nodeSheetSeq.toString())

.id() 变化时 ArkUI 销毁旧组件、创建新组件 ⇒ aboutToAppear 必然重跑。

⚠️ 比 if (flag) 0 : 1 那种写法简单可靠 —— 后者的时序在 V2 里不保证。

顺带修的

backOnce() 里只清了 nodeSheetTripId,没清 editNode ——
下次打开若走到"复用"路径就会拿到上一条的 editing。已补。

验证

  • 服务端:GET /api/v1/trips/227/nodes → node #26 返回 9 个附件 ✅
  • 端上代码:attachsOf 解析、this.photos 回填、ForEach 渲染都正确 ✅
  • 需要用户实测:换两条不同行程分别点编辑,看附件数是否跟着变

提交:ffd6ac5

## 2026-11-05 进展 ### 已定位根因 `@Param editing` 在 ArkUI V2 里是**单向同步**:父组件改 `editNode` 后, 子组件的 `editing` 会更新,但 **`aboutToAppear` 只在首次创建时跑一次**。 ⇒ 换一条行程再点编辑时,`editing` 变了但**回填不重跑** ⇒ `this.photos` 保留上一次的值(可能为空)⇒ 附件带不全。 这正是"列表里能看到、点编辑带不全"的原因:列表用的 `nodes` 数据是新的, 但浮层里的回填是**上一次**的。 ### 修法 加一个重建序号: ```typescript @Local nodeSheetSeq: number = 0; // 点编辑时 this.editNode = n; this.nodeSheetSeq = this.nodeSheetSeq + 1; // ← 序号 +1 this.nodeSheetTripId = this.tripId; // 组件上 FbTripNodeSheet({ ... }) .id('nodeSheet_' + this.nodeSheetSeq.toString()) ``` `.id()` 变化时 ArkUI **销毁旧组件、创建新组件** ⇒ `aboutToAppear` 必然重跑。 ⚠️ 比 `if (flag) 0 : 1` 那种写法简单可靠 —— 后者的时序在 V2 里不保证。 ### 顺带修的 `backOnce()` 里只清了 `nodeSheetTripId`,没清 `editNode` —— 下次打开若走到"复用"路径就会拿到上一条的 `editing`。已补。 ### 验证 - 服务端:`GET /api/v1/trips/227/nodes` → node #26 返回 **9 个附件** ✅ - 端上代码:`attachsOf` 解析、`this.photos` 回填、`ForEach` 渲染都正确 ✅ - 需要用户实测:换两条不同行程分别点编辑,看附件数是否跟着变 提交:`ffd6ac5`
Author
Owner

2026-11-05 已修复

根因找到了:视频走的是 Image

ForEach(this.photos, (ph: FbTripNodePhoto) => {
  Stack() {
    Image(fbImageSrc(ph.key, token))    // ← 不管图片还是视频,都用 Image

视频是 .mp4,Image 组件加载不出任何东西 ⇒ 一个空白块。
所以现象是"图片都在、视频全没"。

FbTripNodePhoto 本来就有 mime 字段(attachsOf 里解析过),完全够判断。

修法

按 mime 分流:

  • mime.startsWith('video/') → 深色底 #2A2320 + 白色 ▶
  • 其他 → Image(不变)

⚠️ 不在编辑浮层取视频首帧:端上解码视频首帧很卡,打开编辑会明显卡顿。
详情页也是用"深色块 + ▶"这个做法。

同时做的:全局表单规范铺开

用户:「不光是这几个,名册、观影、旅程、日程,所有的全部都是一样的。」

新增共享组件 FbFormField.ets(5 个表单原来各写一份,改一处要改五处)。

已改:

文件 改动
FbPersonEditSheet 姓名标必填(红无星号)
FbEventEditSheet 日程 field 两排
FbMovieNewSheet 片名/影院/同看的人/海报/观影照片/简介/备注 全部两排
FbDateTimeField FbDateTimeRow 两排(电影+日程同时生效)

提交:0c2cf9b

待用户验证

  • 编辑有视频的行程,视频应显示深色块 + ▶(不再是空白)
  • 各表单标签应为主题色 Bold,输入框在下一排
  • 电影弹层能滚动(layoutWeight(1),之前 flexShrink(1) 划不动)
## 2026-11-05 已修复 ### 根因找到了:视频走的是 Image ```typescript ForEach(this.photos, (ph: FbTripNodePhoto) => { Stack() { Image(fbImageSrc(ph.key, token)) // ← 不管图片还是视频,都用 Image ``` 视频是 `.mp4`,`Image` 组件加载不出任何东西 ⇒ **一个空白块**。 所以现象是"图片都在、视频全没"。 `FbTripNodePhoto` 本来就有 `mime` 字段(`attachsOf` 里解析过),完全够判断。 ### 修法 按 `mime` 分流: - `mime.startsWith('video/')` → 深色底 `#2A2320` + 白色 ▶ - 其他 → `Image`(不变) ⚠️ 不在编辑浮层取视频首帧:端上解码视频首帧很卡,打开编辑会明显卡顿。 详情页也是用"深色块 + ▶"这个做法。 ### 同时做的:全局表单规范铺开 用户:「不光是这几个,名册、观影、旅程、日程,所有的全部都是一样的。」 新增共享组件 `FbFormField.ets`(5 个表单原来各写一份,改一处要改五处)。 已改: | 文件 | 改动 | |---|---| | `FbPersonEditSheet` | 姓名标必填(红无星号) | | `FbEventEditSheet` | 日程 field 两排 | | `FbMovieNewSheet` | 片名/影院/同看的人/海报/观影照片/简介/备注 全部两排 | | `FbDateTimeField` | `FbDateTimeRow` 两排(电影+日程同时生效) | 提交:`0c2cf9b` ### 待用户验证 - 编辑有视频的行程,视频应显示深色块 + ▶(不再是空白) - 各表单标签应为主题色 Bold,输入框在下一排 - 电影弹层能滚动(`layoutWeight(1)`,之前 `flexShrink(1)` 划不动)
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: laoyang/FamilyBook#55