A 階段最後 milestone、出測試計畫 + 自動化腳本 + 三平台人工 checklist、使用者下週手動跑實機驗證。 Testing artifacts (8 檔、2630 行): - .autoflow/06-testing/m9-5-validation-plan.md: 656 行(4 情境 × 3 平台 × 2 chip = 24 combo) - 4 e2e specs (vitest + RTL + mock WS / mock fetch): - firmware-upgrade-happy-path.spec.ts (357 / 4 cases) - firmware-upgrade-error-recovery.spec.ts (356 / 4 cases + 8 reason it.each) - firmware-r-fw-11-modal-not-closable.spec.ts (303 / 6 cases) - wails-onbeforeclose-firmware-active.spec.ts (217 / 9 cases、含 5 todo 占位 M9-12) - 3 manual checklists: macOS 264 / Windows 234 / Linux 243 行 設計取捨: - 不引入 Playwright/Cypress (visionA-local frontend 沒裝、屬 architect 決策)、走 vitest + mock - E2E 腳本放 06-testing/scripts/ 作 spec doc + 可選實作參考 - 實機驗證走人工 checklist (dongle 插拔 / kill process / SIGTERM 等需要實體互動) MJ3 修復 (M9-4 reviewer round 1 留的 follow-up): - server/internal/api/ws/firmware_ws_test.go: +16/-8 - "type": "firmware:progress" → "firmware_progress" (對齊 firmwareProgressMessage.Type) - "phase" → "stage" (對齊 TDD §4.2 + FirmwareProgress.Stage) - 不動 production code、只 test schema 對齊 執行建議 (給你下週): - Day 1 P0: macOS+Win+Linux × KL520+KL720 happy path (~3h) - Day 2 P1: R-FW-11 + disconnect_during_op + upgrade_mid_failed + 失敗注入 (4h) - Day 3 P2: SIGTERM 延遲關閉 + Wails OnBeforeClose force-quit modal (2-3h) 測試: - go test ./... -race 全綠 (server / wails / frontend 60 tests) - MJ3 修復不破壞既有測試 A 階段開發 6/7 完成 (M9 文件 + M9-1 ~ M9-4.5)、剩 M9-5 實機驗證 (你下週跑)、跑完依結果決定 A 階段交付或派 sub-agent 修。 Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
265 lines
10 KiB
Markdown
265 lines
10 KiB
Markdown
# M9-5 macOS 實機驗證 checklist
|
||
|
||
> 對應 plan:`../m9-5-validation-plan.md`
|
||
> 平台:macOS 14.x(Apple Silicon 或 Intel x86_64)
|
||
> 預估時間:3-4 小時(含 KL520 + KL720 各情境)
|
||
> 執行人:使用者(下週)
|
||
|
||
---
|
||
|
||
## 0. 前置準備(10 分鐘)
|
||
|
||
- [ ] 確認 macOS 版本:`sw_vers`、紀錄:__________
|
||
- [ ] visionA-local A 階段 build(含 M9-1 ~ M9-4 commits)已安裝
|
||
- [ ] 清空舊狀態:`rm -rf ~/Library/Application\ Support/visiona-local/`
|
||
- [ ] 準備硬體:
|
||
- [ ] KL520 KDP1 legacy dongle(若有、最重要):__________
|
||
- [ ] KL520 KDP2 dongle:__________
|
||
- [ ] KL720 dongle:__________
|
||
- [ ] Chrome / Safari / Edge 任一最新版開啟、DevTools 準備好
|
||
- [ ] Terminal 開好、`cd ~/Library/Application\ Support/visiona-local/` 看 log
|
||
|
||
---
|
||
|
||
## 1. Functional 升級流程驗證(90 分鐘)
|
||
|
||
### 1.1 情境 A:KL520 KDP1 → KDP2 完整 4-stage(30 分鐘)
|
||
|
||
**前置**:插 KL520 KDP1 dongle
|
||
|
||
- [ ] 啟動 visionA-local、Wails 視窗顯示
|
||
- [ ] 控制台顯示 server URL(如 `http://127.0.0.1:3721`)
|
||
- [ ] 點「開啟瀏覽器」、Devices 頁出現
|
||
- [ ] Devices 卡片顯示「KL520」+ **紅色 badge** `KDP1 (legacy)`
|
||
- [ ] hover badge 顯示 tooltip:「此韌體為舊版 KDP1...」
|
||
- [ ] 卡片內顯示「升級到 v2.2.0」按鈕(primary、藍)
|
||
- [ ] 點升級按鈕、confirm modal 開啟
|
||
- [ ] modal 標題:「升級韌體」
|
||
- [ ] from/to 顯示:from = `KDP1`、to = `v2.2.0`
|
||
- [ ] 警告文字含「30 秒」「切勿拔除」
|
||
- [ ] 點「開始升級」、modal 切到 upgrading phase
|
||
- [ ] **progress modal 不顯示 ✕ / 取消按鈕**(R-FW-11)
|
||
- [ ] 紅色 banner「⚠ 請勿拔除裝置」顯示
|
||
- [ ] progress bar 從 0% 開始
|
||
- [ ] stage 依序變化:
|
||
- [ ] 「階段 1 / 4:準備(偵測 + 連接裝置)」(preparing、~5%)
|
||
- [ ] 「階段 2 / 4:載入引導程式」(loading、~20%)
|
||
- [ ] 「階段 3 / 4:寫入韌體」(flashing、~50%)
|
||
- [ ] 「階段 4 / 4:驗證完成」(verifying、~90%)
|
||
- [ ] 「已耗時」秒數遞增
|
||
- [ ] 「預估剩餘」秒數顯示(依 etaMs)
|
||
- [ ] **試 ESC 鍵 → modal 不關**
|
||
- [ ] **試點 modal 外部 → modal 不關**
|
||
- [ ] 升級在 60 秒內完成(**紀錄實測時長**:______ 秒)
|
||
- [ ] modal 顯示綠勾 ✓「完成」+ afterVersion `v2.2.0`
|
||
- [ ] 約 1.5 秒後 modal 自動關閉
|
||
- [ ] 右上角 toast:「KL520 #1 升級成功 — 從 KDP1 升級到 v2.2.0(耗時 X 秒)」
|
||
- [ ] toast 停留 6 秒、自動消失
|
||
- [ ] Devices 卡片 FW badge **變綠** + `v2.2.0`
|
||
- [ ] tooltip 變:「韌體為最新版本(v2.2.0)」
|
||
- [ ] Server log 沒有 panic / error(看 `~/Library/Application\ Support/visiona-local/server.log` 最後 100 行)
|
||
|
||
**截圖**:
|
||
- [ ] 升級前 Devices 頁紅 badge:`.autoflow/06-testing/screenshots/macos-A-before.png`
|
||
- [ ] upgrading phase(任一 stage):`.autoflow/06-testing/screenshots/macos-A-upgrading.png`
|
||
- [ ] success toast:`.autoflow/06-testing/screenshots/macos-A-success.png`
|
||
- [ ] 升級後 Devices 頁綠 badge:`.autoflow/06-testing/screenshots/macos-A-after.png`
|
||
|
||
### 1.2 情境 B:KL520 KDP2 short-circuit 3-stage(15 分鐘)
|
||
|
||
**前置**:拔 KDP1 dongle、插 KL520 KDP2(v2.1.0 或 firmware 字串比 bundled current 舊)。或情境 A 跑完後重跑(badge 已綠則無 older 可驗、用「將 bundled VERSION 改為 v2.3.0」模擬 yellow 場景、若太複雜可跳過 yellow 驗證)
|
||
|
||
- [ ] 卡片 badge 顯示 **黃色**(older)或 **綠色**(current、若沒法模擬就接受)
|
||
- [ ] 點升級
|
||
- [ ] progress 序列:**3 stage**(不是 4):
|
||
- [ ] 階段 1 / 3:準備
|
||
- [ ] 階段 2 / 3:寫入韌體(**沒有 loading 階段**)
|
||
- [ ] 階段 3 / 3:驗證完成
|
||
- [ ] 升級在 60 秒內完成(**紀錄實測時長**:______ 秒)
|
||
- [ ] 成功 toast、badge 變綠
|
||
|
||
### 1.3 情境 C:KL720 升級(15 分鐘)
|
||
|
||
**前置**:插 KL720 dongle
|
||
|
||
- [ ] 卡片 badge 顯示綠或黃
|
||
- [ ] 若為黃、點升級
|
||
- [ ] confirm modal 預估時間:「3 分鐘」(180 秒)
|
||
- [ ] progress 序列:3 stage(KL720 預燒 KDP2、走 short-circuit)
|
||
- [ ] 升級在 200 秒內完成(**紀錄實測時長**:______ 秒)
|
||
- [ ] 成功 toast、badge 變綠
|
||
|
||
### 1.4 情境 D:來回升級(15 分鐘)
|
||
|
||
**前置**:第二根 KL520 KDP1 dongle(若沒有則跳過)
|
||
|
||
- [ ] 重複跑情境 A 一次
|
||
- [ ] **驗證沒有 Error 15 SEND_DATA_TOO_LARGE**(KL520 reset bug 應已修)
|
||
- [ ] 連續兩次升級流程都正常
|
||
|
||
### 1.5 多裝置同時連接(15 分鐘)
|
||
|
||
**前置**:KL520 + KL720 同時插上
|
||
|
||
- [ ] Devices 頁兩張卡片
|
||
- [ ] 點 KL520 卡片升級、modal 開啟
|
||
- [ ] 升級 upgrading phase 中、試圖點 KL720 卡片升級
|
||
- [ ] **預期**:被擋(如 409 toast「裝置正在進行其他作業」)或 KL720 modal 開不起來
|
||
- [ ] KL520 升級完成後、KL720 升級可正常進行
|
||
|
||
---
|
||
|
||
## 2. Reliability 失敗注入(45 分鐘)
|
||
|
||
### 2.1 #1 scan_not_found(5 分鐘)
|
||
|
||
- [ ] 拔 USB
|
||
- [ ] 立刻在 Devices 頁試圖點升級按鈕(如果卡片還在)
|
||
- [ ] 預期 error modal「找不到裝置」+「重新插拔後重試」按鈕
|
||
|
||
### 2.2 #3 loader_write_failed(10 分鐘)
|
||
|
||
**注入**:升級進入 loading stage(紅 badge KDP1 → KDP2 流程)時、Terminal 跑 `pkill -9 python` 殺 bridge.py
|
||
|
||
- [ ] error modal 出現
|
||
- [ ] 顯示「引導程式載入失敗」
|
||
- [ ] 顯示「拔插後重試」按鈕
|
||
- [ ] errorCode 出現(如 `FW_LOADER_*`)
|
||
- [ ] 「複製錯誤訊息」按鈕可點、變「已複製 ✓」
|
||
- [ ] **不顯示 brick warning role=note**(recoverable)
|
||
|
||
### 2.3 #4 upgrade_mid_failed(10 分鐘)
|
||
|
||
**注入**:升級進入 flashing stage 時、`pkill -9 python`
|
||
|
||
- [ ] error modal 顯示「韌體寫入失敗、聯絡技術支援」
|
||
- [ ] 顯示「重試」按鈕(**仍 recoverable**、不顯示 brick warning)
|
||
- [ ] errorCode:`FW_UPGRADE_*`
|
||
- [ ] 點「取得協助」(contact support、若有)開 mailto: handler
|
||
|
||
### 2.4 #5 disconnect_during_op — **brick risk 最高**(10 分鐘)
|
||
|
||
**注入**:升級進入 flashing stage 時、**拔 USB**
|
||
|
||
- [ ] error modal 顯示「裝置已斷開」
|
||
- [ ] **顯示 brick warning role=note**(如「裝置可能損壞」)
|
||
- [ ] **不顯示 Retry 按鈕**(destructive reason)
|
||
- [ ] 顯示 **「Contact Support」destructive 按鈕**
|
||
- [ ] 點 Contact Support、開 mailto: handler、subject + body 帶 errorCode
|
||
|
||
### 2.5 #6 timeout(10 分鐘)
|
||
|
||
**注入**:較難在實機重現、可:
|
||
- 拔 USB 但不重新插上、等 KL520 ≥ 60s
|
||
|
||
- [ ] error modal 顯示「操作超時」
|
||
- [ ] 顯示「拔插後重新掃描」按鈕
|
||
|
||
---
|
||
|
||
## 3. UX 驗證(30 分鐘)
|
||
|
||
### 3.1 Badge 4 色(10 分鐘)
|
||
|
||
| State | 觸發 | 紀錄 |
|
||
|-------|------|------|
|
||
| current(綠) | KDP2 firmware = bundled | [ ] 驗 |
|
||
| older(黃) | KDP2 firmware < bundled | [ ] 驗(若無法模擬可跳) |
|
||
| legacy(紅) | KDP1 dongle | [ ] 驗 |
|
||
| unknown(灰) | firmware 字串空 / loading | [ ] 驗(拔 USB 後重新 scan 過渡期) |
|
||
|
||
### 3.2 進度 modal 警告 banner 全程顯示(5 分鐘)
|
||
|
||
- [ ] 升級 preparing 時、banner 顯示
|
||
- [ ] 升級 loading 時、banner 顯示
|
||
- [ ] 升級 flashing 時、banner 顯示
|
||
- [ ] 升級 verifying 時、banner 顯示
|
||
- [ ] 升級 done 時、banner 不再顯示(modal 已切 success phase)
|
||
|
||
### 3.3 Success toast 6 秒停留(5 分鐘)
|
||
|
||
- [ ] 升級成功、toast 出現
|
||
- [ ] **計時 6 秒後 toast 仍可見**(不是預設 4 秒)
|
||
|
||
### 3.4 失敗 modal「複製錯誤訊息」(5 分鐘)
|
||
|
||
- [ ] 點「複製錯誤訊息」按鈕
|
||
- [ ] 按鈕變「已複製 ✓」
|
||
- [ ] 約 2 秒後復原為「複製錯誤訊息」
|
||
- [ ] Terminal 跑 `pbpaste`(macOS)確認剪貼簿內容含 `stage:` / `reason:` / `errorCode:` / `rawError:`
|
||
|
||
### 3.5 「取得協助」mailto: 路徑(5 分鐘)
|
||
|
||
- [ ] destructive reason 的 error modal 點 Contact Support 按鈕
|
||
- [ ] macOS Mail.app 或預設 mail handler 開啟
|
||
- [ ] subject 含 errorCode
|
||
- [ ] body 含技術資訊(stage / reason / deviceId / rawError)
|
||
|
||
---
|
||
|
||
## 4. Integration 驗證(30 分鐘)
|
||
|
||
### 4.1 SIGTERM 延遲關閉(15 分鐘)
|
||
|
||
**前置**:終端機跑 `ps aux | grep visiona-local-server`、紀錄 server PID
|
||
|
||
- [ ] 啟動升級流程(情境 A,慢一點的)
|
||
- [ ] 升級進入 flashing stage 時、Terminal 跑 `kill -TERM <PID>`
|
||
- [ ] **server 不立即退出**
|
||
- [ ] 觀察 `~/Library/Application\ Support/visiona-local/server.log` 最後 50 行
|
||
- [ ] log 含「firmware: N active firmware task(s) detected, delaying shutdown up to ...」
|
||
- [ ] 升級正常完成(firmware task 完成)
|
||
- [ ] log 含「firmware: all firmware tasks completed, proceeding to shutdown」或「firmware: hard timeout ...」
|
||
- [ ] server 完成升級後才退出
|
||
- [ ] Wails 視窗收到 server offline 通知(offline overlay 顯示)
|
||
|
||
### 4.2 Wails OnBeforeClose 攔截(15 分鐘)
|
||
|
||
- [ ] 啟動升級流程
|
||
- [ ] 升級進入 flashing stage 時、點 **Wails 視窗的紅色 ✕ 按鈕**(macOS title bar 左上)
|
||
- [ ] **Wails 視窗不關閉**
|
||
- [ ] Frontend modal 出現:「韌體切換進行中...」
|
||
- [ ] modal 顯示 task info:device name / chip / direction / stage / etaSeconds
|
||
- [ ] modal 顯示「繼續等待」(primary)+「強制關閉」(destructive)按鈕
|
||
- [ ] 點「強制關閉」、預期 **第二層 FORCE 確認**(要輸入「FORCE」字串)
|
||
- [ ] 試輸入「force」小寫 → 確認按鈕 disabled
|
||
- [ ] 試輸入空白 → 確認按鈕 disabled
|
||
- [ ] 輸入「FORCE」大寫 → 確認按鈕 enabled
|
||
- [ ] 點「繼續等待」(不點強制關閉)、modal 關閉、升級流程繼續
|
||
- [ ] 升級正常完成
|
||
- [ ] 升級完成後、再點 ✕ → Wails 視窗正常關閉
|
||
|
||
---
|
||
|
||
## 5. 驗證結果摘要
|
||
|
||
填寫:
|
||
|
||
| 類別 | 結果 | 備註 |
|
||
|------|------|------|
|
||
| §1 Functional | ✅ Pass / ⚠ Partial / ❌ Fail | |
|
||
| §2 Reliability | | |
|
||
| §3 UX | | |
|
||
| §4 Integration | | |
|
||
|
||
**P0 阻擋發布**:______(如「§1.1 升級流程崩潰」)
|
||
**P1 嚴重**:______
|
||
**P2 一般**:______
|
||
**P3 改善**:______
|
||
|
||
升級時長實測:
|
||
|
||
| Combo | 實測 | 護欄 | Pass / Fail |
|
||
|-------|------|------|-----------|
|
||
| KL520 KDP1→KDP2 | __秒 | 60s | |
|
||
| KL520 short-circuit | __秒 | 60s | |
|
||
| KL720 | __秒 | 200s | |
|
||
|
||
---
|
||
|
||
## 6. Bug 回報
|
||
|
||
對每個發現的問題、依 `../m9-5-validation-plan.md §11` 格式回報到 `.autoflow/06-testing/bugs/M9-5-BUG-{NN}.md`。
|
||
|
||
**完成簽核**:________________ 日期:________________
|