fixed highscores
This commit is contained in:
213
supabe_integrate.md
Normal file
213
supabe_integrate.md
Normal file
@ -0,0 +1,213 @@
|
||||
# Spacetris — Supabase Highscore Integration
|
||||
## VS Code Copilot AI Agent Prompt
|
||||
|
||||
You are integrating Supabase highscores into a native C++ SDL3 game called **Spacetris**.
|
||||
|
||||
This is a REST-only integration using Supabase PostgREST.
|
||||
Do NOT use any Supabase JS SDKs.
|
||||
|
||||
---
|
||||
|
||||
## 1. Goal
|
||||
|
||||
Implement a highscore backend using Supabase for these game modes:
|
||||
- classic
|
||||
- challenge
|
||||
- cooperate
|
||||
- versus
|
||||
|
||||
Highscores must be:
|
||||
- Submitted asynchronously on game over
|
||||
- Fetched asynchronously for leaderboard screens
|
||||
- Non-blocking (never stall render loop)
|
||||
- Offline-safe (fail silently)
|
||||
|
||||
---
|
||||
|
||||
## 2. Supabase Configuration
|
||||
|
||||
The following constants are provided at build time:
|
||||
|
||||
```cpp
|
||||
const std::string SUPABASE_URL = "https://xzxpmvyamjvtxpwnjpad.supabase.co";
|
||||
const std::string SUPABASE_ANON_KEY = "sb_publishable_GqQx844xYDizO9-ytlBXfA_MVT6N7yA";
|
||||
````
|
||||
|
||||
All requests go to:
|
||||
|
||||
```
|
||||
{SUPABASE_URL}/rest/v1/highscores
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 3. Database Schema (Already Exists)
|
||||
|
||||
The Supabase table `highscores` has the following fields:
|
||||
|
||||
* score (integer)
|
||||
* lines (integer)
|
||||
* level (integer)
|
||||
* time_sec (integer)
|
||||
* name (string)
|
||||
* game_type ("classic", "versus", "cooperate", "challenge")
|
||||
* timestamp (integer, UNIX epoch seconds)
|
||||
|
||||
---
|
||||
|
||||
## 4. Data Model in C++
|
||||
|
||||
Create a struct matching the database schema:
|
||||
|
||||
```cpp
|
||||
struct HighscoreEntry {
|
||||
int score;
|
||||
int lines;
|
||||
int level;
|
||||
int timeSec;
|
||||
std::string name;
|
||||
std::string gameType;
|
||||
int timestamp;
|
||||
};
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 5. HTTP Layer Requirements
|
||||
|
||||
* Use **libcurl**
|
||||
* Use **JSON** (nlohmann::json or equivalent)
|
||||
* All network calls must run in a worker thread
|
||||
* Never block the SDL main loop
|
||||
|
||||
Required HTTP headers:
|
||||
|
||||
```
|
||||
apikey: SUPABASE_ANON_KEY
|
||||
Authorization: Bearer SUPABASE_ANON_KEY
|
||||
Content-Type: application/json
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 6. Submit Highscore (POST)
|
||||
|
||||
Implement:
|
||||
|
||||
```cpp
|
||||
void SubmitHighscoreAsync(const HighscoreEntry& entry);
|
||||
```
|
||||
|
||||
Behavior:
|
||||
|
||||
* Convert entry to JSON
|
||||
* POST to `/rest/v1/highscores`
|
||||
* On failure:
|
||||
|
||||
* Log error
|
||||
* Do NOT crash
|
||||
* Optionally store JSON locally for retry
|
||||
|
||||
Example JSON payload:
|
||||
|
||||
```json
|
||||
{
|
||||
"score": 123456,
|
||||
"lines": 240,
|
||||
"level": 37,
|
||||
"time_sec": 1820,
|
||||
"name": "P1 & P2",
|
||||
"game_type": "cooperate",
|
||||
"timestamp": 1710000000
|
||||
}
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 7. Fetch Leaderboard (GET)
|
||||
|
||||
Implement:
|
||||
|
||||
```cpp
|
||||
std::vector<HighscoreEntry> FetchHighscores(
|
||||
const std::string& gameType,
|
||||
int limit
|
||||
);
|
||||
```
|
||||
|
||||
REST query examples:
|
||||
|
||||
Classic:
|
||||
|
||||
```
|
||||
?game_type=eq.classic&order=score.desc&limit=20
|
||||
```
|
||||
|
||||
Challenge:
|
||||
|
||||
```
|
||||
?game_type=eq.challenge&order=level.desc,time_sec.asc&limit=20
|
||||
```
|
||||
|
||||
Cooperate:
|
||||
|
||||
```
|
||||
?game_type=eq.cooperate&order=score.desc&limit=20
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 8. Threading Model
|
||||
|
||||
* Use `std::thread` or a simple job queue
|
||||
* Network calls must not run on the render thread
|
||||
* Use mutex or lock-free queue to pass results back to UI
|
||||
|
||||
---
|
||||
|
||||
## 9. Error Handling Rules
|
||||
|
||||
* If Supabase is unreachable:
|
||||
|
||||
* Game continues normally
|
||||
* Leaderboard screen shows "Offline"
|
||||
* Never block gameplay
|
||||
* Never show raw network errors to player
|
||||
|
||||
---
|
||||
|
||||
## 10. Security Constraints
|
||||
|
||||
* API key is public (acceptable for highscores)
|
||||
* Obfuscate key in binary if possible
|
||||
* Do NOT trust client-side data (future server validation planned)
|
||||
|
||||
---
|
||||
|
||||
## 11. File Structure Suggestion
|
||||
|
||||
```
|
||||
/network
|
||||
supabase_client.h
|
||||
supabase_client.cpp
|
||||
|
||||
/highscores
|
||||
highscore_submit.cpp
|
||||
highscore_fetch.cpp
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## 12. Acceptance Criteria
|
||||
|
||||
* Highscores are submitted after game over
|
||||
* Leaderboards load without blocking gameplay
|
||||
* Works for all four game types
|
||||
* Offline mode does not crash or freeze
|
||||
* Code is clean, modular, and SDL3-safe
|
||||
|
||||
---
|
||||
|
||||
## 13. Summary for the Agent
|
||||
|
||||
Integrate Supabase highscores into Spacetris using REST calls from C++ with libcurl. Use async submission and fetching. Support classic, challenge, cooperate, and versus modes. Ensure non-blocking behavior and graceful offline handling.
|
||||
Reference in New Issue
Block a user