Game API

4 min read
  • Building Leaderboards with CRUD
    • Two Types of Leaderboards
    • Setup Steps
    • HTTP Methods (CRUD Operations)
    • How to Add Leaderboard to Your Game
      • Architecture Flow
      • Integration Steps
    • Turn Score & Leaderboard On By Default
      • Option 1: Auto-Initialize Score Counter (Recommended)
      • Option 2: Show Leaderboard on Load

Building Leaderboards with CRUD

Learn to implement dynamic and elementary leaderboard systems

Two Types of Leaderboards

Dynamic Leaderboard
  • Real-time updates as players improve
  • Tracks progress over time
  • Uses UPDATE to modify scores
  • Best for: Games with multiple attempts
Example: High score tracking, speed runs, skill progression
Elementary Leaderboard
  • One-time submission per user
  • Fixed rankings after completion
  • Uses POST only to submit
  • Best for: Quizzes, competitions, challenges
Example: Quiz scores, contest entries, test results

Setup Steps

  1. Log in to your account at pages.opencodingsociety.com/login
  2. Play the game! Then press esc to save your score
  3. Toggle the leaderboard. Choose Dynamic Leaderboard to see your saved score ranked!
⚠️ Important: You must be logged in! Without authentication, the database won't know who owns the stats.

HTTP Methods (CRUD Operations)

GET→ Retrieve / Read
BOTH LEADERBOARDS

Purpose: Retrieve data from the server. Think of this as asking the database for your stats.
Use case: Displaying current leaderboard rankings, checking user scores, loading game state.

View Code Example
// Import javaURI and fetchOptions from config.js
import { javaURI, fetchOptions } from '/assets/js/api/config.js';

// GET request - fetchOptions includes authentication automatically
const res = await fetch(
    `${javaURI}/api/events/SCORE_COUNTER`,
    fetchOptions
);
POST→ Create
BOTH LEADERBOARDS

Purpose: Send data to create a new resource. This adds you to the database initially.
Use case: First-time user registration, initial score submission, creating new game entry.

Elementary Leaderboard: This is the ONLY method you need! One POST per user.
View Code Example
// Import javaURI and fetchOptions from config.js
import { javaURI, fetchOptions } from '/assets/js/api/config.js';

const endpoint = '/api/events/ELEMENTARY_LEADERBOARD';
const url = `${javaURI}${endpoint}`;

// Create payload matching Java backend AlgorithmicEvent structure
const requestBody = {
    payload: {
        user: name,
        score: score,
        gameName: this.gameName
    }
};

// POST - only specify method and body, fetchOptions handles headers
const res = await fetch(
    url,
    {
        ...fetchOptions,
        method: 'POST',
        body: JSON.stringify(requestBody)
    }
);
DELETE→ Remove
BOTH LEADERBOARDS

Purpose: Remove data from the server. Permanently delete a user's entry or stats.
Use case: User requests account deletion, removing invalid entries, clearing old data, resetting progress.

⚠️ Warning: DELETE is permanent! Always confirm before deleting user data.
View Code Example
// Import javaURI and fetchOptions from config.js
import { javaURI, fetchOptions } from '/assets/js/api/config.js';

const url = `${javaURI}/api/events/ELEMENTARY_LEADERBOARD/${id}`;

// DELETE - only specify method, fetchOptions handles authentication
const res = await fetch(
    url,
    {
        ...fetchOptions,
        method: 'DELETE'
    }
);

How to Add Leaderboard to Your Game

Architecture Flow

1. Game Objects (Coin.js, NPC.js) write to GameEnv.stats

2. GameEnv.stats read by GameEnvScore (Score Manager)

3. GameEnvScore displays in Score Counter UI

4. GameEnvScore saves via POST to Backend API stores in Database

5. Leaderboard.js fetches via GET from Backend API displays in Leaderboard UI

Integration Steps

1 Update GameEnv with Score Configuration
// In GameEnv constructor
this.stats = { coinsCollected: 0, levelsCompleted: 0 };
this.scoreConfig = {
    counterVar: 'coinsCollected',
    counterLabel: 'Coins Collected',
    scoreVar: 'coinsCollected'
};
this.scoreManager = null;
2 Update Game Objects to Write to GameEnv.stats
// In Coin.js collect() method
this.gameEnv.stats.coinsCollected++;
3 Import Leaderboard in Your Game Initialization
// In Game.js or your main game file
import Leaderboard from '../Leaderboard.js';

// Create leaderboard instance (inside your game setup)
this.leaderboardInstance = new Leaderboard(this.gameControl, {
    gameName: 'AdventureGame',
    parentId: 'gameContainer',
    initiallyHidden: false // Set to true to hide on load
});
4 Access Score and Leaderboard via Pause Menu

Press ESC during gameplay to open the pause menu. This gives you access to:

  • Toggle Score - Show/hide the score counter
  • Save Score - Submit your score to the backend
  • Toggle Leaderboard - Show/hide the leaderboard

Turn Score & Leaderboard On By Default

Option 1: Auto-Initialize Score Counter (Recommended)

Add this to your Game.js constructor or initialization method:

// In Game.js constructor, after gameControl is created
if (this.gameControl?.gameEnv) {
    this.gameControl.gameEnv.initScoreManager().then(() => {
        // Auto-show score counter on game start
        this.gameControl.gameEnv.scoreManager.toggleScoreDisplay();
    });
}

Option 2: Show Leaderboard on Load

Set initiallyHidden: false when creating the leaderboard:

// In your game initialization
this.leaderboardInstance = new Leaderboard(this.gameControl, {
    gameName: 'AdventureGame',
    parentId: 'gameContainer',
    initiallyHidden: false  // ← Change to false to show on load
});

// Optional: Force positioning for consistent display
setTimeout(() => {
    const container = document.getElementById('leaderboard-container');
    if (container) {
        container.style.position = 'fixed';
        container.style.top = '80px';
        container.style.right = '20px';
        container.style.zIndex = '1000';
    }
}, 100);
Pro Tip: You can combine both options to show score counter AND leaderboard on game start. This is great for competitive games where players want to see rankings immediately!

Course Timeline