任務紀錄 - 列表.md
172 additions, 343 deletions
| ... | ... | @@ -1,25 +1,51 @@ |
| 1 | - # 任務紀錄 | |
| 1 | + # 任務牆記錄 - 取得任務聚合記錄列表 | |
| 2 | - ##SUMMARY | |
| 2 | + ### SUMMARY | |
| 3 | +取得任務牆的聚合記錄列表(分頁查詢)。此 API 會按照 `user_id + master_id` 進行聚合,並計算任務完成狀態與領獎狀態。 | |
| 3 | - 查詢任務看板任務紀錄列表,支援多種條件篩選,包含任務主設定、任務子設定及會員資訊。支援未完成、可領取、已領取等顯示狀態查詢。 | |
| 4 | + **聚合邏輯**: | |
| 5 | +* 當前支援 `ASSIGNED`(指派型)和 `SEQUENTIAL`(序列型)任務 | |
| 6 | +* 按 `user_id + master_id` 聚合(未來支援 `MILESTONE` 時會改為 `user_id + master_id + sub_id`) | |
| 7 | +* 聚合狀態計算:已完成子任務數 < 總子任務數時為 `INCOMPLETE`,否則為 `COMPLETED` | |
| 4 | - ## REFERENCE TABLE | |
| 8 | + #### DisplaySummaryAwardRecordStatus 說明 | |
| 9 | +* `NOT_FINISHED`: 任務未完成 | |
| 10 | +* `CLAIMABLE`: 任務已完成,獎勵可領取 | |
| 11 | +* `CLAIMED`: 獎勵已領取 | |
| 5 | -### 任務相關 | |
| 6 | -* MISSION_SUMMARY_RECORD: 任務統計紀錄表 | |
| 7 | -* MISSION_MASTER_SETTING: 任務主設定表 | |
| 8 | -* MISSION_SUB_SETTING: 任務子設定表 | |
| 9 | -* AWARD_MISSION_SETTING: 任務獎勵設定表 | |
| 10 | - * MISSION_AWARD_RECORD: 任務派獎紀錄表 | |
| 12 | + ### BUSINESS LOGIC | |
| 13 | +1. 子查詢1:計算每個 master 有多少個 sub missions | |
| 14 | +2. 子查詢2:按 `(user_id, master_id, category)` 聚合,計算聚合狀態和最後更新時間 | |
| 15 | +3. JOIN `MissionMaster`(主任務資訊) | |
| 16 | +4. LEFT JOIN `AwardMissionSetting`(獎勵設定,僅 JOIN 主任務獎勵 `sub_id IS NULL`) | |
| 17 | +5. LEFT JOIN `MissionAwardRecord`(獎勵記錄) | |
| 18 | +6. LEFT JOIN `Account`(用戶資訊) | |
| 19 | +7. 套用篩選條件(status, user_id, invite_code, mission 相關欄位等) | |
| 20 | +8. 按 `last_update_time DESC` 排序 | |
| 21 | +9. 分頁返回 | |
| 11 | -### 會員相關 | |
| 12 | - * ACCOUNT: 會員帳號表 | |
| 22 | + ### NOTES | |
| 23 | +* 當前版本僅支援 `ASSIGNED` 和 `SEQUENTIAL` 任務類型 | |
| 24 | +* 未來支援 `MILESTONE` 時需調整聚合邏輯(按 user+master+sub 展開) | |
| 25 | +* `display_status` 為計算欄位,非資料庫直接欄位 | |
| 26 | +* 分頁預設 `page=1`, `per_page=10` | |
| 13 | - ## ATTRIBUTES | |
| 27 | + ### REFERENCE TABLE | |
| 28 | +**核心表** | |
| 29 | +* `MISSION_SUMMARY_RECORD` - 任務摘要記錄表(用於聚合計算) | |
| 30 | +* `USER_MISSION_LOG` - 用戶任務記錄表 | |
| 31 | + | |
| 32 | +**關聯表** | |
| 33 | +* `MISSION_MASTER` - 主任務設定表 | |
| 34 | +* `MISSION_SUB` - 子任務設定表 | |
| 35 | +* `AWARD_MISSION_SETTING` - 任務獎勵設定表 | |
| 36 | +* `MISSION_AWARD_RECORD` - 任務派獎記錄表 | |
| 37 | +* `ACCOUNT` - 用戶帳號表 | |
| 38 | + | |
| 39 | +### ATTRIBUTES | |
| 14 | - * PATH: `/api/features/mission-board/record/summary` | |
| 40 | + * PATH: `/api/features/mission-board/record/aggregated-summaries` | |
| 15 | -| Content-Type | String | * | `"application/json"` | | |
| 16 | - "Content-Type": "application/json", | |
| 17 | 41 | "Authorization": "Bearer jwt-token", |
| 18 | 42 | "x-request-id": "78f91284-d9df-43e6-a8d2-d557273c10bb" |
| 19 | - #### QUERY STRING PARAMETER | |
| 43 | + #### QUERY PARAMETERS | |
| 20 | -| Name | Type/Len | Required(*) | Desc | Default | | |
| 21 | -| ---| ---| ---| ---| --- | | |
| 22 | -| page | Integer | | 頁碼 | 1 | | |
| 23 | -| per_page | Integer | | 每頁筆數 (可選: 20, 50, 100, 500) | 20 | | |
| 24 | -| id | Integer | | 統計紀錄 ID (精準查詢) | | | |
| 25 | -| status | Enum | | 顯示狀態 (NOT_FINISHED=未完成, CLAIMABLE=可領取, CLAIMED=已領取) | | | |
| 26 | -| user__user_id | String | | 身份證字號 (精準查詢) | | | |
| 27 | -| user__invite_code | String | | 會員編號 (精準查詢) | | | |
| 28 | -| mission_master__id | Integer | | 主任務 ID (精準查詢) | | | |
| 29 | -| mission_master__name | String | | 主任務名稱 (模糊搜尋) | | | |
| 30 | -| mission_master__visible_start_time | Datetime | | 主任務可見開始時間 (可見開始時間 <= 此時間) | | | |
| 31 | -| mission_master__visible_end_time | Datetime | | 主任務可見結束時間 (可見結束時間 >= 此時間) | | | |
| 32 | -| mission_sub__id | Integer | | 子任務 ID (精準查詢) | | | |
| 33 | - | mission_sub__name | String | | 子任務名稱 (模糊搜尋) | | | |
| 44 | + | Name | Type/Len | Required(*) | Desc | | |
| 45 | +| ---| ---| ---| --- | | |
| 46 | +| page | Integer | | 頁碼(預設: 1) | | |
| 47 | +| per_page | Integer | | 每頁筆數(預設: 10) | | |
| 48 | +| id | Integer | | 記錄 ID(無實際用途,保留欄位) | | |
| 49 | +| status | Enum | | 顯示狀態(`NOT_FINISHED`, `CLAIMABLE`, `CLAIMED`) | | |
| 50 | +| user__user_id | String | | 用戶 ID(精確匹配) | | |
| 51 | +| user__invite_code | String | | 邀請碼(精確匹配) | | |
| 52 | +| mission_master__id | Integer | | 主任務 ID(精確匹配) | | |
| 53 | +| mission_master__name | String | | 主任務名稱(模糊搜索) | | |
| 54 | +| mission_master__visible_start_time | DateTime | | 可見開始時間(<=) | | |
| 55 | +| mission_master__visible_end_time | DateTime | | 可見結束時間(>=) | | |
| 56 | +| mission_sub__id | Integer | | 子任務 ID(當前版本無效,保留欄位) | | |
| 57 | +| mission_sub__name | String | | 子任務名稱(當前版本無效,保留欄位) | | |
| 34 | -```dpr | |
| 35 | -// Example - 查詢可領取狀態的任務紀錄 | |
| 36 | -GET /api/features/mission-board/record/summary?page=1&per_page=20&status=CLAIMABLE | |
| 37 | - | |
| 38 | -// Example - 查詢特定主任務的紀錄 | |
| 39 | -GET /api/features/mission-board/record/summary?mission_master__id=1&mission_master__name=每日簽到 | |
| 40 | - | |
| 41 | -// Example - 查詢特定會員的任務紀錄 | |
| 42 | -GET /api/features/mission-board/record/summary?user__user_id=A123456789&user__invite_code=ABC123456 | |
| 43 | - | |
| 44 | -// Example - 依時間範圍查詢 | |
| 45 | - GET /api/features/mission-board/record/summary?mission_master__visible_start_time=2024/12/01 00:00:00&mission_master__visible_end_time=2024/12/31 23:59:59 | |
| 58 | + ```swift | |
| 59 | +// Example | |
| 60 | +GET /api/features/mission-board/record/aggregated-summaries?page=1&per_page=10&status=CLAIMABLE&user__user_id=U123456789&mission_master__name=新手任務 | |
| 46 | - * 200 | |
| 61 | + * 200 OK | |
| 47 | - | 1 | data | Dict | | 通用資料包裝 | | |
| 62 | + | 1 | data | Dict | | 回應資料 | | |
| 63 | +| 2 | items | List | | 任務聚合記錄列表 | | |
| 48 | -| 2 | items | List | | 任務紀錄列表 | | |
| 49 | -| 3 | pages | Integer | | 總頁數 | | |
| 50 | -| 3 | first | String | | 第一頁 URL | | |
| 51 | -| 3 | last | String | | 最後一頁 URL | | |
| 52 | -| 3 | prev | String | * | 上一頁 URL | | |
| 53 | - | 3 | next | String | * | 下一頁 URL | | |
| 64 | + | 3 | pages | Integer | | 總頁數 | | |
| 54 | -| Level | Name | Type/Len | Nullable(*) | Desc | Source | | |
| 55 | -| ---| ---| ---| ---| ---| --- | | |
| 56 | -| 3 | id | Integer | | 統計紀錄 ID | `MISSION_SUMMARY_RECORD.ID` | | |
| 57 | -| 3 | user_id | String | | 用戶身份證字號 | `MISSION_SUMMARY_RECORD.USER_ID` | | |
| 58 | -| 3 | sum_count | Integer | * | 總累計次數/分數 | `MISSION_SUMMARY_RECORD.SUM_COUNT` | | |
| 59 | -| 3 | master_id | Integer | | 主任務 ID | `MISSION_SUMMARY_RECORD.MASTER_ID` | | |
| 60 | -| 3 | sub_id | Integer | * | 子任務 ID | `MISSION_SUMMARY_RECORD.SUB_ID` | | |
| 61 | -| 3 | sub_target | Integer | * | 子任務目標數 | `MISSION_SUMMARY_RECORD.SUB_TARGET` | | |
| 62 | -| 3 | category | Enum | | 任務類別 (ASSIGNED=指定型, MILESTONE=多門檻型, SEQUENTIAL=關聯型) | `MISSION_SUMMARY_RECORD.CATEGORY` | | |
| 63 | -| 3 | status | Enum | * | 任務狀態 (INCOMPLETE=未完成, COMPLETED=已完成) | `MISSION_SUMMARY_RECORD.STATUS` | | |
| 64 | -| 3 | display_status | Enum | * | 顯示狀態 (NOT_FINISHED=未完成, CLAIMABLE=可領取, CLAIMED=已領取) | Computed | | |
| 65 | -| 3 | create_time | Datetime | | 建立時間 | `MISSION_SUMMARY_RECORD.CREATE_TIME` | | |
| 66 | -| 3 | update_time | Datetime | * | 更新時間 | `MISSION_SUMMARY_RECORD.UPDATE_TIME` | | |
| 67 | -| 3 | mission_master | Dict | * | 主任務資訊 | - | | |
| 68 | -| 3 | mission_sub | Dict | * | 子任務資訊 | - | | |
| 69 | -| 3 | award_mission_setting | Dict | * | 獎勵設定資訊 | - | | |
| 70 | - | 3 | member | Dict | *| 會員資訊 | - | | |
| 65 | + | Level | Name | Type/Len | Nullable(*) | Desc | | |
| 66 | +| ---| ---| ---| ---| --- | | |
| 67 | +| 3 | user_id | String | | 用戶 ID | | |
| 68 | +| 3 | master_id | Integer | | 主任務 ID | | |
| 69 | +| 3 | category | Enum | | 任務類型 | | |
| 70 | +| 3 | last_update_time | DateTime | * | 最後更新時間 | | |
| 71 | +| 3 | display_status | Enum | * | 顯示狀態(計算欄位) | | |
| 72 | +| 3 | mission_master | Dict | * | 主任務資訊 | | |
| 73 | +| 3 | award_mission_setting | Dict | * | 獎勵設定資訊 | | |
| 74 | +| 3 | award_record | Dict | * | 獎勵記錄資訊 | | |
| 75 | +| 3 | member | Dict | * | 用戶資訊 | | |
| 71 | -| 4 | id | Integer | | 主任務 ID | `MISSION_MASTER_SETTING.ID` | | |
| 72 | -| 4 | name | String | | 主任務名稱 | `MISSION_MASTER_SETTING.NAME` | | |
| 73 | -| 4 | status | Enum | | 主任務狀態 (ACTIVE=啟用, INACTIVE=停用) | `MISSION_MASTER_SETTING.STATUS` | | |
| 74 | -| 4 | category | Enum | | 任務類別 (ASSIGNED=指定型, MILESTONE=多門檻型, SEQUENTIAL=關聯型) | `MISSION_MASTER_SETTING.CATEGORY` | | |
| 75 | -| 4 | description | String | | 主任務描述 | `MISSION_MASTER_SETTING.DESCRIPTION` | | |
| 76 | -| 4 | summary | String | | 主任務摘要 | `MISSION_MASTER_SETTING.SUMMARY` | | |
| 77 | -| 4 | visible_start_time | Datetime | * | 可見開始時間 | `MISSION_MASTER_SETTING.VISIBLE_START_TIME` | | |
| 78 | -| 4 | visible_end_time | Datetime | * | 可見結束時間 | `MISSION_MASTER_SETTING.VISIBLE_END_TIME` | | |
| 79 | -| 4 | activity_start_time | Datetime | * | 活動開始時間 | `MISSION_MASTER_SETTING.ACTIVITY_START_TIME` | | |
| 80 | -| 4 | activity_end_time | Datetime | * | 活動結束時間 | `MISSION_MASTER_SETTING.ACTIVITY_END_TIME` | | |
| 81 | -| 4 | award_end_time | Datetime | * | 獎勵結束時間 | `MISSION_MASTER_SETTING.AWARD_END_TIME` | | |
| 82 | - | 4 | rule_id | Integer | * | 規則 ID | `MISSION_MASTER_SETTING.RULE_ID` | | |
| 76 | + | 4 | id | Integer | | 主任務 ID | `MISSION_MASTER.ID` | | |
| 77 | +| 4 | name | String | | 主任務名稱 | `MISSION_MASTER.NAME` | | |
| 78 | +| 4 | status | Enum | | 任務狀態 | `MISSION_MASTER.STATUS` | | |
| 79 | +| 4 | category | Enum | | 任務類型 | `MISSION_MASTER.CATEGORY` | | |
| 80 | +| 4 | description | String | | 任務描述 | `MISSION_MASTER.DESCRIPTION` | | |
| 81 | +| 4 | summary | String | | 任務摘要 | `MISSION_MASTER.SUMMARY` | | |
| 82 | +| 4 | visible_start_time | DateTime | * | 可見開始時間 | `MISSION_MASTER.VISIBLE_START_TIME` | | |
| 83 | +| 4 | visible_end_time | DateTime | * | 可見結束時間 | `MISSION_MASTER.VISIBLE_END_TIME` | | |
| 84 | +| 4 | activity_start_time | DateTime | * | 活動開始時間 | `MISSION_MASTER.ACTIVITY_START_TIME` | | |
| 85 | +| 4 | activity_end_time | DateTime | * | 活動結束時間 | `MISSION_MASTER.ACTIVITY_END_TIME` | | |
| 86 | +| 4 | award_end_time | DateTime | * | 領獎結束時間 | `MISSION_MASTER.AWARD_END_TIME` | | |
| 83 | -#### mission_sub | |
| 84 | - | |
| 85 | -| Level | Name | Type/Len | Nullable(*) | Desc | Source | | |
| 86 | -| ---| ---| ---| ---| ---| --- | | |
| 87 | -| 4 | id | Integer | | 子任務 ID | `MISSION_SUB_SETTING.ID` | | |
| 88 | -| 4 | name | String | | 子任務名稱 | `MISSION_SUB_SETTING.NAME` | | |
| 89 | -| 4 | activity_type | Enum | | 活動類型 (LOGIN=登入, TRADE=交易, REFERRAL=推薦等) | `MISSION_SUB_SETTING.ACTIVITY_TYPE` | | |
| 90 | -| 4 | category | Enum | | 任務類別 (ASSIGNED=指定型, MILESTONE=多門檻型, SEQUENTIAL=關聯型) | `MISSION_SUB_SETTING.CATEGORY` | | |
| 91 | -| 4 | master_id | Integer | | 主任務 ID | `MISSION_SUB_SETTING.MASTER_ID` | | |
| 92 | - | |
| 93 | -| 4 | sub_id | Integer | * | 子任務 ID | `AWARD_MISSION_SETTING.SUB_ID` | | |
| 94 | - | 4 | award_type | Enum | * | 獎勵類型 (POINT=點數, VOUCHER=票券) | `AWARD_MISSION_SETTING.AWARD_TYPE` | | |
| 87 | + | 4 | sub_id | Integer | * | 子任務 ID | `AWARD_MISSION_SETTING.SUB_ID` | | |
| 88 | +| 4 | award_type | Enum | * | 獎勵類型 | `AWARD_MISSION_SETTING.AWARD_TYPE` | | |
| 95 | -| 4 | award_group_id | String | * | 獎項群組 ID | `AWARD_MISSION_SETTING.AWARD_GROUP_ID` | | |
| 96 | -| 4 | category | Enum | | 任務類別 (ASSIGNED=指定型, MILESTONE=多門檻型, SEQUENTIAL=關聯型) | `AWARD_MISSION_SETTING.CATEGORY` | | |
| 97 | -| 4 | quota | Integer | * | 配額限制 | `AWARD_MISSION_SETTING.QUOTA` | | |
| 98 | -| 4 | create_time | Datetime | | 建立時間 | `AWARD_MISSION_SETTING.CREATE_TIME` | | |
| 99 | - | 4 | update_time | Datetime | * | 更新時間 | `AWARD_MISSION_SETTING.UPDATE_TIME` | | |
| 89 | + | 4 | category | Enum | | 任務類型 | `AWARD_MISSION_SETTING.CATEGORY` | | |
| 90 | +| 4 | quota | Integer | * | 獎勵配額 | `AWARD_MISSION_SETTING.QUOTA` | | |
| 91 | +| 4 | create_time | DateTime | | 建立時間 | `AWARD_MISSION_SETTING.CREATE_TIME` | | |
| 92 | +| 4 | update_time | DateTime | * | 更新時間 | `AWARD_MISSION_SETTING.UPDATE_TIME` | | |
| 93 | +#### award_record | |
| 94 | + | |
| 95 | +| Level | Name | Type/Len | Nullable(*) | Desc | Source | | |
| 96 | +| ---| ---| ---| ---| ---| --- | | |
| 97 | +| 4 | id | Integer | | 獎勵記錄 ID | `MISSION_AWARD_RECORD.ID` | | |
| 98 | +| 4 | user_id | String | | 用戶 ID | `MISSION_AWARD_RECORD.USER_ID` | | |
| 99 | +| 4 | invite_code | String | | 邀請碼 | `ACCOUNT.INVITE_CODE` | | |
| 100 | +| 4 | award_setting_id | Integer | * | 獎勵設定 ID | `MISSION_AWARD_RECORD.AWARD_SETTING_ID` | | |
| 101 | +| 4 | sub_id | Integer | * | 子任務 ID | `MISSION_AWARD_RECORD.SUB_ID` | | |
| 102 | +| 4 | master_id | Integer | * | 主任務 ID | `MISSION_AWARD_RECORD.MASTER_ID` | | |
| 103 | +| 4 | category | Enum | | 任務類型 | `MISSION_AWARD_RECORD.CATEGORY` | | |
| 104 | +| 4 | tier | Integer | * | 層級 | `MISSION_AWARD_RECORD.TIER` | | |
| 105 | +| 4 | award_code | String | * | 獎勵代碼 | `MISSION_AWARD_RECORD.AWARD_CODE` | | |
| 106 | +| 4 | status | Enum | * | 派獎狀態 | `MISSION_AWARD_RECORD.STATUS` | | |
| 107 | +| 4 | award_error | String | * | 派獎錯誤訊息 | `MISSION_AWARD_RECORD.AWARD_ERROR` | | |
| 108 | +| 4 | request_no | String | * | 請求編號 | `MISSION_AWARD_RECORD.REQUEST_NO` | | |
| 109 | +| 4 | create_time | DateTime | | 建立時間 | `MISSION_AWARD_RECORD.CREATE_TIME` | | |
| 110 | +| 4 | update_time | DateTime | * | 更新時間 | `MISSION_AWARD_RECORD.UPDATE_TIME` | | |
| 111 | +| 4 | trans_id | String | * | 交易 ID | `MISSION_AWARD_RECORD.TRANS_ID` | | |
| 112 | + | |
| 100 | -| 4 | id | String | | 會員身份證字號 | `ACCOUNT.ID` | | |
| 101 | - | 4 | invite_code | String | * | 推薦碼/會員編號 | `ACCOUNT.INVITE_CODE` | | |
| 113 | + | 4 | id | String | | 用戶 ID | `ACCOUNT.ID` | | |
| 114 | +| 4 | invite_code | String | * | 邀請碼 | `ACCOUNT.INVITE_CODE` | | |
| 102 | 115 | "data": { |
| 103 | 116 | "pagination": { |
| 104 | 117 | "page": 1, |
| 105 | - "per_page": 20, | |
| 106 | - "pages": 1, | |
| 107 | - "total": 5, | |
| 108 | - "first": "/api/features/mission-board/record/summary?page=1&per_page=20", | |
| 109 | - "last": "/api/features/mission-board/record/summary?page=1&per_page=20", | |
| 110 | - "prev": null, | |
| 111 | - "next": null | |
| 118 | + "per_page": 10, | |
| 119 | + "total": 100, | |
| 120 | + "pages": 10 | |
| 112 | 121 | }, |
| 113 | 122 | "items": [ |
| 114 | 123 | { |
| 115 | - "id": 5, | |
| 116 | - "user_id": "E123456789", | |
| 117 | - "sum_count": 1, | |
| 124 | + "user_id": "U123456789", | |
| 118 | 125 | "master_id": 1, |
| 119 | - "sub_id": 1, | |
| 120 | - "sub_target": 1, | |
| 121 | 126 | "category": "ASSIGNED", |
| 122 | - "status": "COMPLETED", | |
| 127 | + "last_update_time": "2026-03-19T10:30:00", | |
| 123 | 128 | "display_status": "CLAIMABLE", |
| 124 | - "create_time": "2026/03/10 10:00:00", | |
| 125 | - "update_time": "2026/03/10 10:05:00", | |
| 126 | 129 | "mission_master": { |
| 127 | 130 | "id": 1, |
| 128 | - "name": "每日簽到任務", | |
| 131 | + "name": "新手任務", | |
| 129 | 132 | "status": "ACTIVE", |
| 130 | 133 | "category": "ASSIGNED", |
| 131 | - "description": "每天登入即可完成任務", | |
| 132 | - "summary": "連續簽到獲得更多獎勵", | |
| 133 | - "visible_start_time": "2026/03/01 00:00:00", | |
| 134 | - "visible_end_time": "2026/03/31 23:59:59", | |
| 135 | - "activity_start_time": "2026/03/01 00:00:00", | |
| 136 | - "activity_end_time": "2026/03/31 23:59:59", | |
| 137 | - "award_end_time": "2026/04/07 23:59:59", | |
| 138 | - "rule_id": 1 | |
| 134 | + "description": "完成所有新手任務", | |
| 135 | + "summary": "新手獎勵", | |
| 136 | + "visible_start_time": "2026-01-01T00:00:00", | |
| 137 | + "visible_end_time": "2026-12-31T23:59:59", | |
| 138 | + "activity_start_time": "2026-01-01T00:00:00", | |
| 139 | + "activity_end_time": "2026-12-31T23:59:59", | |
| 140 | + "award_end_time": "2026-12-31T23:59:59" | |
| 139 | 141 | }, |
| 140 | - "mission_sub": { | |
| 141 | - "id": 1, | |
| 142 | - "name": "每日登入", | |
| 143 | - "activity_type": "LOGIN", | |
| 144 | - "category": "ASSIGNED", | |
| 145 | - "master_id": 1 | |
| 146 | - }, | |
| 147 | 142 | "award_mission_setting": { |
| 148 | - "id": 1, | |
| 149 | - "sub_id": 1, | |
| 143 | + "id": 100, | |
| 150 | 144 | "master_id": 1, |
| 145 | + "sub_id": null, | |
| 151 | 146 | "award_type": "POINT", |
| 152 | 147 | "award_content": "100點", |
| 153 | - "award_code": "DAILY_LOGIN_100", | |
| 154 | - "award_group_id": "1", | |
| 148 | + "award_code": "NEWBIE_POINT", | |
| 155 | 149 | "category": "ASSIGNED", |
| 156 | - "quota": 1, | |
| 157 | - "create_time": "2026/03/01 00:00:00", | |
| 150 | + "quota": 1000, | |
| 151 | + "create_time": "2026-01-01T00:00:00", | |
| 158 | 152 | "update_time": null |
| 159 | 153 | }, |
| 160 | - "member": { | |
| 161 | - "id": "E123456789", | |
| 162 | - "invite_code": "MEM12345" | |
| 163 | - } | |
| 164 | - }, | |
| 165 | - { | |
| 166 | - "id": 4, | |
| 167 | - "user_id": "D987654321", | |
| 168 | - "sum_count": 1, | |
| 154 | + "award_record": { | |
| 155 | + "id": 5000, | |
| 156 | + "user_id": "U123456789", | |
| 157 | + "invite_code": "ABC123", | |
| 158 | + "award_setting_id": 100, | |
| 159 | + "sub_id": null, | |
| 169 | 160 | "master_id": 1, |
| 170 | - "sub_id": 1, | |
| 171 | - "sub_target": 1, | |
| 172 | 161 | "category": "ASSIGNED", |
| 173 | - "status": "COMPLETED", | |
| 174 | - "display_status": "CLAIMED", | |
| 175 | - "create_time": "2026/03/10 09:30:00", | |
| 176 | - "update_time": "2026/03/10 09:40:00", | |
| 177 | - "mission_master": { | |
| 178 | - "id": 1, | |
| 179 | - "name": "每日簽到任務", | |
| 180 | - "status": "ACTIVE", | |
| 181 | - "category": "ASSIGNED", | |
| 182 | - "description": "每天登入即可完成任務", | |
| 183 | - "summary": "連續簽到獲得更多獎勵", | |
| 184 | - "visible_start_time": "2026/03/01 00:00:00", | |
| 185 | - "visible_end_time": "2026/03/31 23:59:59", | |
| 186 | - "activity_start_time": "2026/03/01 00:00:00", | |
| 187 | - "activity_end_time": "2026/03/31 23:59:59", | |
| 188 | - "award_end_time": "2026/04/07 23:59:59", | |
| 189 | - "rule_id": 1 | |
| 162 | + "tier": null, | |
| 163 | + "award_code": "NEWBIE_POINT", | |
| 164 | + "status": "UNCLAIMED", | |
| 165 | + "award_error": null, | |
| 166 | + "request_no": null, | |
| 167 | + "create_time": "2026-03-19T10:30:00", | |
| 168 | + "update_time": null, | |
| 169 | + "trans_id": null | |
| 190 | 170 | }, |
| 191 | - "mission_sub": { | |
| 192 | - "id": 1, | |
| 193 | - "name": "每日登入", | |
| 194 | - "activity_type": "LOGIN", | |
| 195 | - "category": "ASSIGNED", | |
| 196 | - "master_id": 1 | |
| 197 | - }, | |
| 198 | - "award_mission_setting": { | |
| 199 | - "id": 1, | |
| 200 | - "sub_id": 1, | |
| 201 | - "master_id": 1, | |
| 202 | - "award_type": "POINT", | |
| 203 | - "award_content": "100點", | |
| 204 | - "award_code": "DAILY_LOGIN_100", | |
| 205 | - "award_group_id": "1", | |
| 206 | - "category": "ASSIGNED", | |
| 207 | - "quota": 1, | |
| 208 | - "create_time": "2026/03/01 00:00:00", | |
| 209 | - "update_time": null | |
| 210 | - }, | |
| 211 | 171 | "member": { |
| 212 | - "id": "D987654321", | |
| 213 | - "invite_code": "MEM67890" | |
| 172 | + "id": "U123456789", | |
| 173 | + "invite_code": "ABC123" | |
| 214 | 174 | } |
| 215 | - }, | |
| 216 | - { | |
| 217 | - "id": 3, | |
| 218 | - "user_id": "C555666777", | |
| 219 | - "sum_count": 1, | |
| 220 | - "master_id": 1, | |
| 221 | - "sub_id": 1, | |
| 222 | - "sub_target": 1, | |
| 223 | - "category": "ASSIGNED", | |
| 224 | - "status": "COMPLETED", | |
| 225 | - "display_status": "CLAIMABLE", | |
| 226 | - "create_time": "2026/03/10 09:00:00", | |
| 227 | - "update_time": "2026/03/10 09:15:00", | |
| 228 | - "mission_master": { | |
| 229 | - "id": 1, | |
| 230 | - "name": "每日簽到任務", | |
| 231 | - "status": "ACTIVE", | |
| 232 | - "category": "ASSIGNED", | |
| 233 | - "description": "每天登入即可完成任務", | |
| 234 | - "summary": "連續簽到獲得更多獎勵", | |
| 235 | - "visible_start_time": "2026/03/01 00:00:00", | |
| 236 | - "visible_end_time": "2026/03/31 23:59:59", | |
| 237 | - "activity_start_time": "2026/03/01 00:00:00", | |
| 238 | - "activity_end_time": "2026/03/31 23:59:59", | |
| 239 | - "award_end_time": "2026/04/07 23:59:59", | |
| 240 | - "rule_id": 1 | |
| 241 | - }, | |
| 242 | - "mission_sub": { | |
| 243 | - "id": 1, | |
| 244 | - "name": "每日登入", | |
| 245 | - "activity_type": "LOGIN", | |
| 246 | - "category": "ASSIGNED", | |
| 247 | - "master_id": 1 | |
| 248 | - }, | |
| 249 | - "award_mission_setting": { | |
| 250 | - "id": 1, | |
| 251 | - "sub_id": 1, | |
| 252 | - "master_id": 1, | |
| 253 | - "award_type": "POINT", | |
| 254 | - "award_content": "100點", | |
| 255 | - "award_code": "DAILY_LOGIN_100", | |
| 256 | - "award_group_id": "1", | |
| 257 | - "category": "ASSIGNED", | |
| 258 | - "quota": 1, | |
| 259 | - "create_time": "2026/03/01 00:00:00", | |
| 260 | - "update_time": null | |
| 261 | - }, | |
| 262 | - "member": { | |
| 263 | - "id": "C555666777", | |
| 264 | - "invite_code": "MEM55566" | |
| 265 | 175 | } |
| 266 | - }, | |
| 267 | - { | |
| 268 | - "id": 2, | |
| 269 | - "user_id": "B222333444", | |
| 270 | - "sum_count": 0, | |
| 271 | - "master_id": 1, | |
| 272 | - "sub_id": 1, | |
| 273 | - "sub_target": 1, | |
| 274 | - "category": "ASSIGNED", | |
| 275 | - "status": "INCOMPLETE", | |
| 276 | - "display_status": "NOT_FINISHED", | |
| 277 | - "create_time": "2026/03/10 08:30:00", | |
| 278 | - "update_time": "2026/03/10 08:45:00", | |
| 279 | - "mission_master": { | |
| 280 | - "id": 1, | |
| 281 | - "name": "每日簽到任務", | |
| 282 | - "status": "ACTIVE", | |
| 283 | - "category": "ASSIGNED", | |
| 284 | - "description": "每天登入即可完成任務", | |
| 285 | - "summary": "連續簽到獲得更多獎勵", | |
| 286 | - "visible_start_time": "2026/03/01 00:00:00", | |
| 287 | - "visible_end_time": "2026/03/31 23:59:59", | |
| 288 | - "activity_start_time": "2026/03/01 00:00:00", | |
| 289 | - "activity_end_time": "2026/03/31 23:59:59", | |
| 290 | - "award_end_time": "2026/04/07 23:59:59", | |
| 291 | - "rule_id": 1 | |
| 292 | - }, | |
| 293 | - "mission_sub": { | |
| 294 | - "id": 1, | |
| 295 | - "name": "每日登入", | |
| 296 | - "activity_type": "LOGIN", | |
| 297 | - "category": "ASSIGNED", | |
| 298 | - "master_id": 1 | |
| 299 | - }, | |
| 300 | - "award_mission_setting": { | |
| 301 | - "id": 1, | |
| 302 | - "sub_id": 1, | |
| 303 | - "master_id": 1, | |
| 304 | - "award_type": "POINT", | |
| 305 | - "award_content": "100點", | |
| 306 | - "award_code": "DAILY_LOGIN_100", | |
| 307 | - "award_group_id": "1", | |
| 308 | - "category": "ASSIGNED", | |
| 309 | - "quota": 1, | |
| 310 | - "create_time": "2026/03/01 00:00:00", | |
| 311 | - "update_time": null | |
| 312 | - }, | |
| 313 | - "member": { | |
| 314 | - "id": "B222333444", | |
| 315 | - "invite_code": "MEM22233" | |
| 316 | - } | |
| 317 | - }, | |
| 318 | - { | |
| 319 | - "id": 1, | |
| 320 | - "user_id": "A123456789", | |
| 321 | - "sum_count": 0, | |
| 322 | - "master_id": 1, | |
| 323 | - "sub_id": 1, | |
| 324 | - "sub_target": 1, | |
| 325 | - "category": "ASSIGNED", | |
| 326 | - "status": "INCOMPLETE", | |
| 327 | - "display_status": "NOT_FINISHED", | |
| 328 | - "create_time": "2026/03/10 08:00:00", | |
| 329 | - "update_time": "2026/03/10 08:30:00", | |
| 330 | - "mission_master": { | |
| 331 | - "id": 1, | |
| 332 | - "name": "每日簽到任務", | |
| 333 | - "status": "ACTIVE", | |
| 334 | - "category": "ASSIGNED", | |
| 335 | - "description": "每天登入即可完成任務", | |
| 336 | - "summary": "連續簽到獲得更多獎勵", | |
| 337 | - "visible_start_time": "2026/03/01 00:00:00", | |
| 338 | - "visible_end_time": "2026/03/31 23:59:59", | |
| 339 | - "activity_start_time": "2026/03/01 00:00:00", | |
| 340 | - "activity_end_time": "2026/03/31 23:59:59", | |
| 341 | - "award_end_time": "2026/04/07 23:59:59", | |
| 342 | - "rule_id": 1 | |
| 343 | - }, | |
| 344 | - "mission_sub": { | |
| 345 | - "id": 1, | |
| 346 | - "name": "每日登入", | |
| 347 | - "activity_type": "LOGIN", | |
| 348 | - "category": "ASSIGNED", | |
| 349 | - "master_id": 1 | |
| 350 | - }, | |
| 351 | - "award_mission_setting": { | |
| 352 | - "id": 1, | |
| 353 | - "sub_id": 1, | |
| 354 | - "master_id": 1, | |
| 355 | - "award_type": "POINT", | |
| 356 | - "award_content": "100點", | |
| 357 | - "award_code": "DAILY_LOGIN_100", | |
| 358 | - "award_group_id": "1", | |
| 359 | - "category": "ASSIGNED", | |
| 360 | - "quota": 1, | |
| 361 | - "create_time": "2026/03/01 00:00:00", | |
| 362 | - "update_time": null | |
| 363 | - }, | |
| 364 | - "member": { | |
| 365 | - "id": "A123456789", | |
| 366 | - "invite_code": "MEM123" | |
| 367 | - } | |
| 368 | - } | |
| 369 | 176 | ] |
| 370 | 177 | } |
| 371 | -| 400 | INVALID_PARAMETER | Invalid parameter | 參數格式錯誤 | | |
| 372 | -| 401 | UNAUTHORIZED | Unauthorized | 未授權存取 | | |
| 373 | -| 403 | FORBIDDEN | Forbidden | 無權限存取 | | |
| 374 | - | 500 | INTERNAL_SERVER_ERROR | Internal server error | 伺服器內部錯誤 | | |
| 178 | + | 400 | ValidationError.INVALID_INPUT | Invalid input data | 輸入資料格式錯誤 | | |
| 179 | +| 422 | ValidationError.SCHEMA_VALIDATION_FAILED | Schema validation failed | Schema 驗證失敗 | | |
| 180 | + | |
| 181 | +### CODE REFERENCE | |
| 182 | + | |
| 183 | +**Route**: [route.py](http://../route.py#L34-L47) | |
| 184 | + | |
| 185 | +```python | |
| 186 | +@bp.get('/aggregated-summaries') | |
| 187 | +@bp.doc(summary='取得任務紀錄', description='取得任務紀錄列表') | |
| 188 | +@bp.auth_required(auth) | |
| 189 | +@read_permission_required(Feature.MISSION_BOARD_RECORD) | |
| 190 | +@bp.input(GetMissionBoardAggregateRecordPageInSchema, location='query') | |
| 191 | +@bp.output(GetMissionBoardAggregateRecordPageOutSchema, status_code=200) | |
| 192 | +``` | |
| 193 | + | |
| 194 | +**Schema**: [schema.py](http://../schema.py) | |
| 195 | +* Input: `GetMissionBoardAggregateRecordPageInSchema` (lines 14-27) | |
| 196 | +* Output: `GetMissionBoardAggregateRecordPageOutSchema` (lines 109-110) | |
| 197 | + | |
| 198 | +**Service**: [service.py](http://../service.py) | |
| 199 | +* `get_mission_board_aggregate_records_pagination()` (lines 20-153) | |
| 200 | +* `compose_mission_board_summary_record_query_filters()` (lines 156-216) | |
| 201 | + | |
| 202 | +**Presenter**: [presenter.py](http://../presenter.py) | |
| 203 | +* `display_mission_board_summary_record()` (lines 15-124) |