Files
CFDivePlatform/openspec/specs/course-scheduling/spec.md
T
a620906209 0cd1047b10
Run Tests / test (pull_request) Successful in 30s
docs(openspec): 補齊所有 spec 缺少的 Purpose section 與規格標頭
repo 內 35/38 份既有 spec 都是舊版歸檔流程留下的原始 delta 內容(`##
ADDED Requirements`,缺標題與 Purpose),openspec CLI 現版本嚴格驗證
(--strict)會報錯或警告。逐一補上:

- 缺標題/Purpose 的 30 份:加上 `# <name> Specification` 標題 + 依內容
  撰寫的 Purpose 段落,`## ADDED Requirements` 改回 `## Requirements`
- compose-cloud-baseline、scheduler-container:已有標題與
  Requirements,只補 Purpose 包裝
- provider-verification:已有標題與 Purpose,只需把
  `## ADDED Requirements` 改回 `## Requirements`
- admin-user-management、notification-email:各有一條 requirement 缺
  SHALL/MUST 關鍵字(純敘述句或表格),補上規範用語,內容不變

`openspec validate --specs --strict`:38/38 全過(原本 4/38)。純文件
補齊,未變更任何 requirement 的實質內容或行為描述。

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_011LpcY9b7y9x4fusHBTXciQ
2026-08-03 04:11:06 +08:00

4.0 KiB
Raw Blame History

course-scheduling Specification

Purpose

定義教練建立與管理開課時段、取消時段時對既有預約的 cascade 處理、名額自動管理,以及會員查詢可用時段的行為。

Requirements

Requirement: Provider 建立開課時段

Provider SHALL 能為自己擁有的 DivingOffer 建立開課時段,指定日期、開始時間、人數上限。

Scenario: 成功建立時段

  • WHEN Provider 送出 POST /api/provider/schedules,包含合法的 diving_offer_idscheduled_date(未來日期)、start_timemax_participants(≥1
  • THEN 系統建立 CourseSchedulestatus 為 open,回傳 201 與新時段資料

Scenario: 不可為他人課程建立時段

  • WHEN Provider 送出的 diving_offer_id 屬於其他 Provider
  • THEN 系統回傳 403 Forbidden

Scenario: 日期不可為過去

  • WHEN scheduled_date 早於今天
  • THEN 系統回傳 422,錯誤訊息指出日期無效

Requirement: Provider 管理既有時段

Provider SHALL 能更新或取消自己的開課時段。

Scenario: 更新時段資訊

  • WHEN Provider 送出 PUT /api/provider/schedules/{id},修改 start_timemax_participants
  • THEN 系統更新時段資料,回傳更新後內容

Scenario: 取消時段

  • WHEN Provider 送出 DELETE /api/provider/schedules/{id}
  • THEN 系統將時段 status 改為 cancelled,不實體刪除;cascade 處理所有相關 Booking(詳見下方 Requirement

Scenario: 不可修改他人時段

  • WHEN Provider 嘗試修改不屬於自己的時段
  • THEN 系統回傳 403 Forbidden

Requirement: 取消時段的 Booking Cascade 處理

Provider 取消時段時,系統 SHALL 在同一 DB transaction 內處理該時段下所有活躍 Booking,並明確定義各狀態的 cascade 規則。

Scenario: pending Booking cascade 為 provider_cancelled

  • WHEN Provider 取消時段,時段下存在 status 為 pending 的 Booking
  • THEN 這些 Booking status 全部改為 provider_cancelled

Scenario: confirmed Booking cascade 為 provider_cancelled

  • WHEN Provider 取消時段,時段下存在 status 為 confirmed 的 Booking
  • THEN 這些 Booking status 全部改為 provider_cancelledcurrent_participants 不需調整(時段已取消)

Scenario: 終態 Booking 不受 cascade 影響

  • WHEN Provider 取消時段,時段下存在 status 為 completedrejectedexpiredmember_cancelledprovider_cancelled 的 Booking
  • THEN 這些 Booking status 維持不變

Scenario: cascade 在同一 transaction 內完成

  • WHEN Provider 取消時段
  • THEN 時段狀態更新與所有 Booking cascade 更新在同一 DB transaction 內完成;任一失敗則全部 rollback,API 回傳 500

Requirement: 時段人數自動管理

系統 SHALL 在預約確認時自動累計 current_participants,並於額滿時將時段 status 改為 fullcurrent_participants 只計算 confirmed 人數,pending 不佔位。

Scenario: 預約確認後人數更新

  • WHEN Provider 確認一筆 Bookingconfirmed),booking 的 participants 為 N
  • THEN course_schedules.current_participants 增加 N;若達到 max_participants 則 status 改為 full

Scenario: 預約取消後人數釋放

  • WHEN 一筆 confirmed 狀態的 Booking 被取消(member_cancelled 或 provider_cancelled
  • THEN current_participants 減少對應人數;若原本為 full 則 status 改回 open

Requirement: Member 查詢可用時段

Member SHALL 能查詢指定課程的可用開課時段列表。

Scenario: 取得開放時段

  • WHEN 任何人(含未登入)送出 GET /api/diving-offers/{id}/schedules
  • THEN 系統回傳該課程 status 為 open、日期未過的時段列表(含剩餘名額 remaining_spots),依日期升冪排序

Scenario: 已滿時段不顯示

  • WHEN 時段 status 為 full
  • THEN 不包含在上述列表中