# Webhook

## Webhook Integration

### Overview

When using the **UserID & Webhook** campaign type, game results are not displayed on an in-game leaderboard. Instead, the results are sent directly to your server via a webhook POST request.

This allows you to collect game data in real time and integrate it with your own system — whether that's a database, CRM, analytics platform, or even a simple Google Sheet.

***

### How It Works

1. Your website embeds the game with a `userid` parameter
2. The user plays the game
3. Upon completion, our system sends the game result to your **Webhook URL** via POST
4. Your server processes the data and returns a status code

```
Your Website                          Branded Mini-Games
    |                                        |
    |-- userid (via URL parameter) --------->|
    |                                        |  User plays the game
    |<-- Webhook POST (game result) ---------|
    |                                        |
    |-- Return "S" (success) --------------->|
```

<figure><img src="/files/ciHyskL5jLXFQf16ZTqn" alt=""><figcaption></figcaption></figure>

***

### URL Parameter

Append the `userid` as a GET parameter when embedding the game:

```
https://branded.mini-games.io/?php=landing@game&campaign_no=YOUR_CAMPAIGN_NO&userid=T4g4fLTa
```

> For details on generating and managing user IDs, see the User ID Setup Guide.

***

### Webhook Data

The following parameters are sent to your Webhook URL via **POST**:

| Parameter  | Required | Description                                 | Example               |
| ---------- | -------- | ------------------------------------------- | --------------------- |
| `userid`   | Yes      | Unique user identifier sent by your system  | `T4g4fLTa`            |
| `tx_id`    | Yes      | Unique transaction ID for each game play    | `234234`              |
| `time`     | Yes      | Date and time when the user played the game | `2025-04-10 06:39:23` |
| `score`    | Yes      | Score the user achieved                     | `3500`                |
| `playtime` | Yes      | Play duration in seconds                    | `20`                  |

#### Data Format

You can choose the data format in the Studio settings:

* **default** — standard form POST (`application/x-www-form-urlencoded`)
* **json** — JSON format (`application/json`)

***

### Return Code

Your webhook endpoint **must** return a status code to confirm receipt:

| Code | Description                                                    |
| ---- | -------------------------------------------------------------- |
| `S`  | Successfully received and processed                            |
| `F`  | Failed. You may include a reason, e.g., `F: Score is missing.` |

***

### Server-Side Example (Node.js)

```javascript
app.post('/webhook', (req, res) => {
  const { userid, tx_id, time, score, playtime } = req.body;

  // Validate required fields
  if (!userid || !tx_id || !score) {
    return res.send('F: Missing required fields.');
  }

  // Store the data in your database
  db.insert({ userid, tx_id, time, score, playtime });

  return res.send('S');
});
```

***

### Google Sheets Integration (No Server Required)

If you don't have a backend server, you can use **Google Apps Script** to receive webhook data directly into a Google Sheet. This is ideal for promotions, contests, or quick setups.

#### Step 1: Create a Google Sheet

1. Go to [Google Sheets](https://sheets.google.com) and create a new spreadsheet
2. In the first row, add headers:

| A            | B          | C          | D        | E         | F            |
| ------------ | ---------- | ---------- | -------- | --------- | ------------ |
| **Received** | **userid** | **tx\_id** | **time** | **score** | **playtime** |

#### Step 2: Open Apps Script

1. In your Google Sheet, go to **Extensions > Apps Script**
2. Delete any existing code and paste the following:

```javascript
function doPost(e) {
  var sheet = SpreadsheetApp.getActiveSpreadsheet().getActiveSheet();
  var data = JSON.parse(e.postData.contents);

  sheet.appendRow([
    new Date(),
    data.userid,
    data.tx_id,
    data.time,
    data.score,
    data.playtime
  ]);

  return ContentService.createTextOutput('S');
}
```

3. Click **Save** (Ctrl+S / Cmd+S)

#### Step 3: Deploy as Web App

1. Click **Deploy > New deployment**
2. Click the gear icon and select **Web app**
3. Configure the settings:

| Setting        | Value                        |
| -------------- | ---------------------------- |
| Description    | Webhook receiver             |
| Execute as     | **Me** (your Google account) |
| Who has access | **Anyone**                   |

4. Click **Deploy**
5. Authorize the app when prompted (review permissions and allow)
6. Copy the **Web app URL** — this is your Webhook URL

> The URL looks like: `https://script.google.com/macros/s/AKfycb.../exec`

<figure><img src="/files/Rmiwym3yST00tUIvHcqp" alt=""><figcaption></figcaption></figure>

#### Step 4: Set the Webhook URL in Studio

1. Go to your campaign's **UserID & Webhook** settings
2. Paste the Web app URL into the **Webhook URL** field
3. Set **Result data format** to **json**
4. Click **Update the URL information**

#### Important Notes

* **Result data format must be set to `json`** — Google Apps Script's `JSON.parse(e.postData.contents)` expects JSON format. If set to `default`, the data will not be parsed correctly.
* **Re-deploy after code changes** — Every time you edit the Apps Script code, you must create a **New deployment** (not just save). The URL changes with each new deployment, so update the Webhook URL in Studio accordingly.
* **Google account permissions** — The script runs under your Google account. The first deployment requires authorization to access your Google Sheets.
* **Rate limits** — Google Apps Script has a daily quota (approximately 20,000 requests/day for free accounts). For high-traffic campaigns, consider a dedicated server instead.
* **Response time** — Apps Script may have a slight delay (1-3 seconds). This does not affect the game experience, as the webhook is sent asynchronously after the game ends.
* **Data privacy** — Game result data is stored in your Google Sheet. Ensure your spreadsheet sharing settings are appropriate for your data privacy requirements.

***

### Testing Your Webhook

You can test your webhook endpoint using curl:

```bash
curl -X POST https://your-webhook-url \
  -H "Content-Type: application/json" \
  -d '{"userid":"testuser","tx_id":"123456","time":"2025-04-10 06:39:23","score":"3500","playtime":"20"}'
```

Expected response: `S`

***

### Building a Leaderboard with Webhook Data

The webhook data you receive can be used to build your own leaderboard. Below are no-code and low-code options that receive scores and display rankings on your website.

***

#### Option 1: Zapier + KeepTheScore (Recommended)

Use [Zapier](https://zapier.com/) to receive the webhook and push scores to [KeepTheScore](https://keepthescore.com/), which provides a hosted leaderboard with real-time updates.

```
Game End → Webhook POST → Zapier (receive) → KeepTheScore API (push score)
                                                      ↓
                                        Embed leaderboard on your website
```

**Step 1: Create a Zap**

1. Go to [Zapier](https://zapier.com/) and create a new Zap
2. **Trigger**: Choose "Webhooks by Zapier" → "Catch Hook"
3. Copy the webhook URL provided by Zapier
4. Paste this URL into your campaign's **Webhook URL** field in Studio
5. Set **Result data format** to `json`

**Step 2: Create a KeepTheScore Board**

1. Go to [keepthescore.com](https://keepthescore.com/) and create a new leaderboard
2. Note your board ID from the URL (e.g., `https://keepthescore.com/board/xxxxxx/`)
3. Get your API key from the board settings

**Step 3: Connect Zapier to KeepTheScore**

1. **Action**: Choose "Webhooks by Zapier" → "POST"
2. URL: `https://keepthescore.com/api/xxxxxx/score/`
3. Payload Type: `json`
4. Data: Map `userid` → player name, `score` → score value

**Step 4: Embed on Your Website**

```html
<iframe src="https://keepthescore.com/board/xxxxxx/leaderboard/"
        width="100%" height="600" frameborder="0"></iframe>
```

| Feature           | Details                                                                               |
| ----------------- | ------------------------------------------------------------------------------------- |
| Real-time updates | Scores appear automatically                                                           |
| Filters           | All-time, daily, weekly, monthly                                                      |
| Pricing           | Basic free, premium features paid                                                     |
| WordPress         | [WP plugin](https://wordpress.com/plugins/keep-the-score) available (shortcode embed) |

***

#### Option 2: Airtable (Webhook + Data Management + Embed)

[Airtable](https://airtable.com/) can receive webhooks directly, store data, and embed a sorted view as a leaderboard.

**Step 1: Create a Base**

Create an Airtable base with these fields:

| Field    | Type             |
| -------- | ---------------- |
| userid   | Single line text |
| score    | Number           |
| tx\_id   | Single line text |
| time     | Date             |
| playtime | Number           |

**Step 2: Set Up Webhook Automation**

1. Go to **Automations** → Create automation
2. Trigger: **When webhook received**
3. Copy the webhook URL and paste it into Studio's Webhook URL field
4. Action: **Create record** — map the webhook fields to your table columns

**Step 3: Create a Leaderboard View**

1. Create a new **Grid view** named "Leaderboard"
2. Sort by `score` descending
3. Hide unnecessary columns (tx\_id, playtime, etc.)

**Step 4: Embed on Your Website**

1. Click **Share and sync** → **Embed this view**
2. Copy the iframe code

| Feature         | Details                                   |
| --------------- | ----------------------------------------- |
| Webhook         | Built-in, no middleware needed            |
| Data management | Filter, search, export                    |
| Pricing         | Free (1,000 records), Team $20/user/month |
| Limitation      | Embed uses Airtable's default styling     |

***

#### Option 3: Google Sheets + Common Ninja Widget

Combine the Google Sheets integration above with [Common Ninja's Leaderboard Widget](https://www.commoninja.com/widgets/leaderboard) for a visual leaderboard.

**Step 1:** Set up Google Sheets webhook receiver (see above)

**Step 2:** Create a Common Ninja leaderboard widget

1. Go to [commoninja.com/widgets/leaderboard](https://www.commoninja.com/widgets/leaderboard)
2. Create a new widget and configure the [API Integration](https://help.commoninja.com/hc/en-us/articles/17188672146205-How-to-Set-Up-API-Integration) to read from your Google Sheet
3. Customize the design (colors, layout, number of entries)

**Step 3:** Embed the widget on your website

```html
<!-- Common Ninja embed code (from widget settings) -->
<div class="commoninja_component" comp-type="leaderboard" comp-id="YOUR_WIDGET_ID"></div>
<script src="https://cdn.commoninja.com/sdk/latest/commonninja.js"></script>
```

| Feature     | Details                                                                         |
| ----------- | ------------------------------------------------------------------------------- |
| Design      | Highly customizable                                                             |
| Data source | Google Sheets, Airtable, or API                                                 |
| WordPress   | [WP plugin](https://www.commoninja.com/widgets/leaderboard/wordpress) available |
| Pricing     | Free tier available                                                             |

***

#### Option 4: Leaderboarded

[Leaderboarded.com](https://leaderboarded.com/) — dedicated leaderboard SaaS with API and WordPress support.

| Feature   | Details                                                            |
| --------- | ------------------------------------------------------------------ |
| API       | [REST API](https://leaderboarded.com/docs/api/) for pushing scores |
| Themes    | 40+ leaderboard themes                                             |
| Embed     | iframe, real-time updates                                          |
| WordPress | [WP shortcode embed](https://leaderboarded.com/docs/wordpress/)    |
| Pricing   | Free tier, embed requires Business plan                            |

***

#### Which Option Should I Choose?

|                          | Zapier + KeepTheScore | Airtable           | Sheets + Common Ninja | Leaderboarded     |
| ------------------------ | --------------------- | ------------------ | --------------------- | ----------------- |
| **Easiest setup**        | Good                  | Best               | Moderate              | Good              |
| **Leaderboard design**   | Good (themes)         | Basic              | Best (customizable)   | Good (40+ themes) |
| **Data management**      | Limited               | Best               | Good (Sheets)         | Limited           |
| **No middleware needed** | No (Zapier)           | Yes                | No (Apps Script)      | No (Zapier/Make)  |
| **WordPress plugin**     | Yes                   | No                 | Yes                   | Yes               |
| **Best for**             | Quick leaderboard     | Data + leaderboard | Custom design         | Themed boards     |


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://support.brandedminigames.com/webhook/webhook.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
