Nhiệm vụ hằng ngày và hằng tuần — một lý do để quay lại
Giờ đây mỗi ván kết thúc đều đẩy tiến một loạt nhiệm vụ hằng ngày và hằng tuần, trao XP ngay khi bạn hoàn thành một nhiệm vụ, và nạp điểm cho một bảng xếp hạng hằng tuần mới.

Nói đơn giản
Cho đến nay, sự tiến bộ duy nhất trong opolyx là một phần thưởng một lần khi thắng một ván. Chẳng có gì để theo đuổi ngày qua ngày. Nhiệm vụ thay đổi điều đó: một nhóm nhỏ mục tiêu hằng ngày và hằng tuần tiến lên mỗi khi bạn kết thúc một ván, dù thắng hay thua.
Bạn không phải nhận thưởng và cũng chẳng có nút nào để bấm — ngay khi một ván kết thúc, máy chủ kiểm tra các nhiệm vụ của bạn, ghi có những nhiệm vụ đã hoàn thành, và cộng XP thẳng vào cấp của bạn. Sáu nhiệm vụ chạy cùng lúc:
- Hằng ngày — chơi 1 ván, chơi 3 ván, thắng 1 ván.
- Hằng tuần — chơi 10 ván, thắng 3 ván, thắng 3 ván ở chế độ Tốc độ.
- Nhiệm vụ hằng ngày đặt lại mỗi ngày; nhiệm vụ hằng tuần đặt lại mỗi thứ Hai.
| Nhiệm vụ | Tần suất | Mục tiêu | Phần thưởng |
|---|---|---|---|
| Chơi một ván | Hằng ngày | 1 | +50 XP |
| Tiếp tục chơi | Hằng ngày | 3 | +120 XP |
| Thắng một ván | Hằng ngày | 1 | +150 XP |
| Đều đặn | Hằng tuần | 10 ván | +300 XP |
| Đang thắng liên tiếp | Hằng tuần | 3 chiến thắng | +400 XP |
| Ác quỷ tốc độ | Hằng tuần | 3 chiến thắng Tốc độ | +400 XP |
Kết thúc các ván cũng kiếm được điểm bảng xếp hạng hằng tuần, nên bạn càng chơi nhiều thì leo càng cao. Bảng đặt lại mỗi tuần, cho mọi người một cơ hội sạch để lên đỉnh vào sáng thứ Hai.
Cho người thích chi tiết kỹ thuật
Lược đồ cho một vòng lặp giữ chân đầy đủ vốn đã tồn tại nhưng nằm im và không được đọc — missions / user_missions (tần suất, mục tiêu, tiến độ, xp_reward) và weekly_top (week_start, điểm). Migration 0031 đấu nối nó vào đường trao thưởng khi kết thúc ván sẵn có thay vì phát minh ra thứ gì mới.
Khi kết thúc một ván thật, daemon duyệt qua từng người chơi là người thật và gọi một RPC service-role duy nhất. Nó đẩy tiến mọi nhiệm vụ mà lần kết thúc này thỏa mãn trong chu kỳ hiện tại, trao XP lần đầu tiên vượt qua một mục tiêu, và cộng vào tổng điểm hằng tuần:
-- grant_play_rewards(p_game, p_user, p_won): security definer, service-role only
-- daily cadence = current_date; weekly = date_trunc('week', now())
-- weekly_top.points += 20 (play) + (won ? 200 : 0) + mission_xp_earned
-- idempotent per (game_id, user_id) via the game_play_grants guard; bots skipped| Khớp sự kiện | Đẩy tiến | Điểm |
|---|---|---|
| {"event":"play"} | Mỗi lần kết thúc | +20 |
| {"event":"win"} | Chỉ chiến thắng | +200 |
| {"event":"play","mode":"speed"} | Chỉ ván Tốc độ | +20 |
Tính bất biến (idempotency) là một hàng chốt chặn theo từng (ván, người dùng), nên một commit chạy lại không bao giờ trả hai lần. Một cái bẫy leo thang đặc quyền lộ ra lúc áp dụng: đặc quyền mặc định của Postgres cấp EXECUTE trên các hàm mới cho anon/authenticated, và revoke … from public không gỡ bỏ điều đó. Một hàm trao thưởng SECURITY DEFINER mà bất kỳ người dùng đã đăng nhập nào cũng gọi được chính là một nông trại XP — đã sửa bằng revoke … from public, anon, authenticated để chỉ {postgres, service_role} mới gọi được, giống như award_game_winner.
Hiện phần thưởng chỉ là XP — xu thuộc về hướng kiếm tiền, thứ cần một chỗ tiêu trước đã. Cả bảng trên trang Chơi lẫn Bảng xếp hạng đều đọc tiến độ chu kỳ hiện tại ở phía client, với tuần được neo vào cùng mốc thứ Hai mà Postgres dùng nên hai bên không bao giờ lệch nhau.
