討論 #1461
是由 陳國瑋 於 28 天 前更新
## 討論目的
確認 Dashboard mockup 既有「30 日充電用量」區塊的期間、指標與資料語意。本票只定義唯讀圖表與摘要資訊,不改變交易、電量或充電作業邏輯。
## Source of Truth
Redmine attachment #1110 a17-operations-dashboard.html 的既有設計包含:
- 標題「30 日充電用量」。
- 圖表指標切換:kWh/Sessions。
- 三項摘要:有效充電量、充電 Sessions、時間使用率。
- Mockup 中的數字均為展示假資料,正式功能必須由 Dashboard API 回傳。
原 mockup 沒有 7 日、90 日或自訂日期範圍選擇。
## USG-DEC-001:V1 固定最近 30 個案場日曆日
**狀態:已確認(2026-09-03,Ken)**
### 使用者會看到什麼
- V1 固定顯示最近 30 個案場日曆日,包含使用者開啟 Dashboard 的今天。
- 日期邊界依該 building 的 timezone 判定,不使用瀏覽器時區,也不硬編碼 A17。
- 今天尚未結束,因此今天的圖表數值屬於進行中資料;畫面不得暗示今天已完成結算。
- 保留 mockup 的 kWh/Sessions 指標切換;切換指標不改變 30 日日期範圍。
- V1 不提供 7 日、90 日或自訂日期範圍 selector。
### 日期例子
若案場時區日期為 2026-09-03,30 個日期 bucket 為 2026-08-05 至 2026-09-03,共 30 個日曆日;其中 2026-09-03 是進行中的今天。
### Backend 要開發的內容
- 依指定 buildingId 及該案場 timezone 產生固定 30 日查詢範圍。
- Dashboard read model 回傳 rangeStartDate、rangeEndDate、timezone,以及圖表使用的每日 kWh/Sessions series。
- 30 日範圍的日期計算由 Backend 統一負責,Frontend 不自行以 browser timezone 重算。
- 本區塊透過 REST 取得;不新增 Usage WebSocket event。
- 查詢只讀取、彙整既有資料,不回寫 Transaction、MeterValue、Billing 或其他業務資料。
### Frontend 要開發的內容
- 標題維持「30 日充電用量」,不新增日期範圍 selector。
- 依 Backend 回傳的 rangeStartDate/rangeEndDate/timezone 顯示同一段 30 日資料。
- kWh/Sessions 切換只切換圖表指標,不觸發 7/90 日或自訂範圍查詢。
- 今天的 bucket 必須能被辨識為進行中資料。
- Loading、Empty、Partial、Error 與缺少日期資料的呈現方式另行確認。
## USG-DEC-002:有效充電量只採已完成交易的最終電量
**狀態:已確認(2026-09-03,Ken)**
### 指標定義
有效充電量使用下列唯讀聚合語意:
validEnergyKWh = SUM(energy_consumed) / 1000
納入條件:
- Transaction status 必須是 COMPLETED。
- energy_consumed 必須非 null 且大於或等於 0。
- energy_consumed 單位為 Wh,API 聚合後轉成 kWh。
- 0 Wh 的 COMPLETED 交易可納入資料集合,但對有效充電量的加總貢獻為 0;不得只因為 0 Wh 就自行改成 ERROR。
不納入有效充電量:
- ACTIVE:尚未形成最終 energy_consumed,完成後才納入。
- CANCELLED、ERROR。
- energy_consumed 為 null 或負值的 COMPLETED 交易。
### Partial 語意
- 如果查詢範圍內存在 energy_consumed 為 null 或負值的 COMPLETED 交易,Backend 將其排除於加總,並回傳 excludedEnergyTransactionCount。
- 上述資料品質缺漏會使 Usage 區塊標示 PARTIAL;不得靜默忽略,也不得把缺值當成 0。
- ACTIVE、CANCELLED、ERROR 因本來就不符合本指標定義,不計入 excludedEnergyTransactionCount。
### Backend 要開發的內容
- 使用 e_transactions 已保存的 status 與 energy_consumed 進行 read-only aggregation。
- Overview DTO 回傳 validEnergyKWh、excludedEnergyTransactionCount 及 section/source status。
- 不從 raw MeterValue 為 ACTIVE 或缺值交易另外估算電量。
- 不呼叫帳務重算、不修改 Transaction,也不建立第二套 energyConsumed 寫入公式。
- 每日 kWh series 使用相同的 Completed/energy_consumed eligibility;跨日交易歸屬哪一個日期另案確認。
### Frontend 要開發的內容
- 「有效充電量」顯示 Backend 回傳的 validEnergyKWh,不自行從每日 bucket 重算。
- 提供簡短說明:「僅包含已完成交易;進行中交易完成後納入」。
- section status 為 PARTIAL 時顯示部分完成交易電量缺漏,不能仍標示為完整資料。
- Frontend 不把 null、缺漏或排除筆數轉為 0。
### A17 驗證結果
以 2026-08-05 至 2026-09-03 的 A17 唯讀資料套用此 eligibility:
- 78 筆 COMPLETED 中,77 筆正電量、1 筆 0 Wh。
- null 與負值均為 0 筆,因此 excludedEnergyTransactionCount = 0。
- validEnergyKWh = 2,171.915 kWh。
- 另有 1 筆 ACTIVE,不在本指標內,待交易完成後才納入。
此數字只是當下 baseline,不是所有案場的固定驗收值。
## USG-DEC-003:每日資料依交易開始日歸屬
**狀態:已確認(2026-09-03,Ken)**
### 日期歸屬規則
- 符合 USG-DEC-002 的整筆 COMPLETED 交易,依 start_timestamp 在該 building timezone 對應的日曆日期歸入一個 daily bucket。
- 同一交易的全部有效 energy_consumed 都歸在開始日期;即使 stop_timestamp 落在隔日或更晚,也不拆分至其他日期。
- kWh 與 Sessions 圖表共用相同的開始日 bucket 規則;Sessions 的 eligibility 仍另案確認。
- 30 日查詢範圍依交易開始日判定,採 rangeStartDate 00:00(含)至 rangeEndDate 次日 00:00(不含)的半開區間,邊界以 building timezone 為準。
- 一筆在範圍內開始、目前仍 ACTIVE 的交易不先估算;交易完成後,於下一次 REST refresh 納入原本的開始日 bucket,因此先前日期的 bucket 可能被補上最終數值。
### 使用者會看到什麼
- 圖表 tooltip/說明文字標示「用量依交易開始日歸屬」。
- 跨日交易不會在圖表被切成兩筆 Session,也不會把單筆 energyConsumed 拆到兩個日期。
- 此圖表代表「依 Session 開始日整理的充電使用趨勢」,不是逐日電網 MeterValue 的精確日切報表。
### Backend 要開發的內容
- 以 building timezone 將 start_timestamp 轉為 date bucket,不使用 browser timezone,也不硬編碼 A17。
- 每日 kWh series 對符合 USG-DEC-002 的交易加總整筆 energy_consumed。
- REST response 維持固定 30 個日期 bucket;跨日交易不執行 MeterValue day-splitting。
- 不修改 startTimestamp、stopTimestamp、energyConsumed 或任何交易/帳務資料。
### Frontend 要開發的內容
- 直接使用 Backend 回傳的 bucket date、kWh 與 Sessions,不自行重新分組。
- kWh/Sessions 切換時日期軸完全一致。
- 在 tooltip 或區塊說明中顯示開始日歸屬語意,避免被誤解為逐時電表報表。
### A17 影響說明
A17 基線中 78 筆 COMPLETED 有 10 筆跨日。依本決策,這 10 筆的整筆電量都歸到各自開始日;A17 數字只用於驗證行為,不成為其他案場的固定比例或規則。
## USG-DEC-004:充電 Sessions 只計算已完成且有正電量的交易
**狀態:已確認(2026-09-03,Ken)**
### 指標定義
validSessionCount = COUNT(Transaction)
納入條件:
- Transaction status = COMPLETED。
- energy_consumed > 0。
不納入條件:
- COMPLETED 但 energy_consumed = 0:代表沒有實際產生充電量,不計入充電 Sessions;此情況本身不自動視為 ERROR 或 PARTIAL。
- ACTIVE:交易完成且取得最終正電量後才納入。
- CANCELLED、ERROR。
- energy_consumed 為 null 或負值的 COMPLETED:不納入,並依 USG-DEC-002 回傳 excludedEnergyTransactionCount、將 Usage 區塊標示 PARTIAL。
### 日期歸屬
- 符合條件的 Session 依 USG-DEC-003 歸入 building timezone 的交易開始日 bucket。
- kWh 與 Sessions 使用相同的 30 日日期軸及 startTimestamp 歸屬方式。
- 本決策只定義哪些交易算一個 Session,不改變交易生命週期或狀態。
### Backend 要開發的內容
- Overview DTO 回傳 validSessionCount,並在每個 daily bucket 回傳對應 sessionCount。
- validSessionCount 與 daily sessionCount 必須使用同一套 COMPLETED + positive energy eligibility。
- 不沿用目前未區分 status/energy 的 transactions.size() 作為 Dashboard Sessions。
- 不為 0 Wh、ACTIVE、CANCELLED 或 ERROR 交易虛構有效 Session。
- 不修改 Transaction,也不觸發 Stop、重算或補償流程。
### Frontend 要開發的內容
- 摘要「充電 Sessions」顯示 Backend 回傳的 validSessionCount。
- Sessions 圖表模式使用 Backend daily sessionCount,不自行從其他欄位推算。
- Tooltip/說明文字顯示「僅計算已完成且有充電量的交易」。
- 0 筆必須顯示 0;資料來源失敗或 null 則依 Empty/Partial/Error 規則呈現,不得混為 0。
### A17 驗證結果
以 2026-08-05 至 2026-09-03 的 A17 唯讀資料套用此規則:
- 77 筆 COMPLETED 且 energy_consumed > 0,因此 validSessionCount = 77。
- 1 筆 COMPLETED 為 0 Wh,不計入。
- 1 筆 ACTIVE 尚未完成,不計入。
- 此數字只作為當下 baseline,不是其他案場的固定驗收值。
## USG-DEC-005:V1 移除時間使用率
**狀態:已確認(2026-09-03,Ken)**
### 決策原因
- 原 mockup 的「時間使用率」原意是:有效 Session duration 合計占全案場 Connector 理論可使用時數的比例。
- 此比例不是即時負載、設備健康度或實際有功輸出時間,單獨顯示時容易被誤解。
- 住宅、公用/私人設備比例與使用時段不同,缺乏共同 benchmark 時,低或高百分比無法直接判斷好壞。
- 使用目前 Connector 數當分母會忽略期間內新增/停用設備;建立完整歷史分母又會使 V1 過度複雜。
- Dashboard V1 以簡單、可理解的唯讀資訊為主,因此不實作這項指標。
### Frontend 影響
- 從「30 日充電用量」摘要中移除「時間使用率」label、數值、tooltip 與 loading/error placeholder。
- 不用其他百分比直接沿用「時間使用率」名稱。
- 第三個摘要位置要顯示哪一項替代資訊,另案逐題確認;在確認前不自行填入新指標。
- 區塊仍保留已確認的有效充電量、充電 Sessions 與 kWh/Sessions 圖表切換。
### Backend 影響
- Dashboard overview 不需要回傳 timeUtilizationPercent、availableConnectorHours 或 utilization denominator。
- 不查詢歷史 Connector 啟用區間,也不新增設備 availability history。
- 既有 durationSeconds 欄位與其他帳務/交易用途不受影響。
### V1 明確不包含
- 時間使用率 threshold、紅黃綠燈或告警。
- 跨案場利用率排名。
- 為了此指標新增 Connector 啟停歷史資料表。
- 任何會改變設備、交易或排程的操作。
## V1 不開發
- 7 日、90 日或自訂日期範圍。
- Usage history export。
- Dashboard 內的交易或 MeterValue 明細表。
- Usage WebSocket publisher。
- 任何電量、Session 或時間使用率的寫入、修正或重算操作。
## Acceptance Criteria
- [ ] 每次 response 的 rangeStartDate 至 rangeEndDate 依案場 timezone 恰好涵蓋 30 個日曆日。
- [ ] rangeEndDate 是案場當天,且該日可明確辨識為進行中。
- [ ] kWh 與 Sessions 使用相同 30 日範圍及 Backend 回傳的開始日 bucket;跨日交易不拆分。
- [ ] UI 不出現 7 日、90 日或自訂日期範圍控制。
- [ ] 切換 kWh/Sessions 不影響 Dashboard WebSocket 連線。
- [ ] 有效充電量只加總符合 USG-DEC-002 的 COMPLETED energy_consumed,正確由 Wh 轉成 kWh,並依 USG-DEC-003 歸入開始日。
- [ ] validSessionCount 與每日 sessionCount 只計算 COMPLETED 且 energy_consumed > 0,並使用同一開始日 bucket。
- [ ] 異常 Completed 的排除筆數可見且區塊標示 PARTIAL;ACTIVE 不進行 MeterValue 估算。
- [ ] UI 與 API 均不包含時間使用率、available Connector hours 或其 threshold。
- [ ] 所有資料皆為唯讀彙整,不產生任何業務狀態變更。
## 已驗證的程式碼與 A17 基線(非需求決策)
### 現有程式碼
- e_transactions 已有 status、start_timestamp、stop_timestamp、meter_start、meter_stop、energy_consumed 與 duration_seconds。
- TransactionService 在交易完成時以 meterStop - meterStart 寫入 energyConsumed,單位為 Wh,並將狀態改為 COMPLETED。
- 現有 Transaction status 包含 ACTIVE、COMPLETED、CANCELLED、ERROR。
- MeterValueTariffCalculationService 另有較完整的 MeterValue 分段與帳務邊界處理;是否需要把該複雜度帶入 Dashboard Usage,尚未決定。
### A17 Read-only Baseline
查詢時間:2026-09-03;案場日曆範圍:2026-08-05 至 2026-09-03。
- Building:BLD000000014;4 個 Charge Points、12 個 Connectors。
- 最近 30 日共有 78 筆 COMPLETED、1 筆 ACTIVE。
- 78 筆 COMPLETED 均有 meterStart、meterStop 與 energyConsumed。
- 77 筆 energyConsumed > 0、1 筆等於 0、0 筆 null、0 筆負值。
- 唯一的 0 Wh COMPLETED 交易持續 15 秒,StopReason 為 EVDisconnected;77 筆正電量交易最短 69 秒。此差異只作為 Sessions 定義的討論依據。
- 77 筆有效 Sessions 的 durationSeconds 合計 1,124,353 秒(312.320 小時)。
- 其中 38 筆 durationSeconds 與 stopTimestamp - startTimestamp 相差 -1 秒,全部都是秒級精度截斷,沒有小時級偏移;以 timestamp 計算則為 312.331 小時。
- A17 目前有 12 個 Connector,全部隸屬 enabled Charge Point,且最近 30 日沒有新增 Connector。
- 若以目前 12 個 Connector × 30 日 × 24 小時為分母,A17 時間使用率 baseline 為 3.6148%;mockup 的 4.08% 仍是展示假資料。
- 78 筆的 energyConsumed 均與 meterStop - meterStart 一致。
- COMPLETED 正電量合計為 2,171.915 kWh。
- 其中 10 筆 COMPLETED 跨越案場日曆日,表示後續仍須明確決定每日 bucket 依交易開始日、完成日或 MeterValue 實際日切分。
以上數字只用於驗證方案與資料品質,不是所有案場的固定規則,也不是正式驗收期待值。
## 待確認事項
- [x] 「有效充電量」只加總 COMPLETED 且 energy_consumed 非 null、非負的交易;異常 Completed 排除並標示 Partial(USG-DEC-002)。
- [x] kWh 與 Sessions 的每日 bucket 均依 building timezone 的交易開始日歸屬;跨日不拆分(USG-DEC-003)。
- [x] 「充電 Sessions」只計算 COMPLETED 且 energy_consumed > 0 的交易;依開始日歸屬(USG-DEC-004)。
- [x] V1 移除「時間使用率」,不定義分子、分母、threshold 或 Backend 欄位(USG-DEC-005)。
- [ ] 移除時間使用率後,第三個摘要位置顯示哪一項替代資訊? 「時間使用率」的分子、分母與無資料語意。
- [ ] 缺少單日資料時應顯示 0、null 或 Partial。
- [ ] Empty/Partial/Error 的具體文案與圖表呈現。
## 需求管理狀態
- Parent:#1422
- Requirement status:**待確認(時間範圍、有效充電量、開始日歸屬、Sessions 及移除時間使用率已確認;替代摘要與資料狀態待確認)** status:**待確認(時間範圍、有效充電量、開始日歸屬與 Sessions 已確認;時間使用率及資料狀態待確認)**
- Confirmed decision:USG-DEC-001、USG-DEC-002、USG-DEC-003、USG-DEC-004、USG-DEC-005 decision:USG-DEC-001、USG-DEC-002、USG-DEC-003、USG-DEC-004
- Final specification:所有 Dashboard 區塊確認後再整併至 #1422 v1.0 文件
- Implementation tickets:需求鎖定後才建立 FE/BE/QA child issues
返回