Added Task 7: Set Up DNS (Cloudflare) before Nginx configuration. Michael needs to: 1. Add A record: webhook.firefrostgaming.com → 63.143.34.217 2. Set to DNS only (proxy OFF) 3. Verify DNS propagation with dig Renumbered subsequent tasks (Nginx is now Task 8, Holly prep is Task 9). Chronicler #40
1403 lines
38 KiB
Markdown
1403 lines
38 KiB
Markdown
# Firefrost Gaming - Subscription Automation Guide
|
|
|
|
**Version:** 1.0
|
|
**Date:** March 23, 2026
|
|
**Author:** Chronicler #40
|
|
**Audience:** Holly (Lead Builder) + Michael (for Discord bot setup)
|
|
**Purpose:** Automate subscriber tier assignment from Paymenter purchase to in-game ranks
|
|
|
|
---
|
|
|
|
## 📋 TABLE OF CONTENTS
|
|
|
|
1. [Overview](#overview)
|
|
2. [Architecture](#architecture)
|
|
3. [Prerequisites](#prerequisites)
|
|
4. [Part 1: Discord Bot Setup](#part-1-discord-bot-setup)
|
|
5. [Part 2: Discord Roles Configuration](#part-2-discord-roles-configuration)
|
|
6. [Part 3: LuckPerms Groups & Permissions](#part-3-luckperms-groups-permissions)
|
|
7. [Part 4: LuckPerms Discord Integration](#part-4-luckperms-discord-integration)
|
|
8. [Part 5: Paymenter Webhook Configuration](#part-5-paymenter-webhook-configuration)
|
|
9. [Testing & Verification](#testing-verification)
|
|
10. [Troubleshooting](#troubleshooting)
|
|
|
|
---
|
|
|
|
## 🎯 OVERVIEW
|
|
|
|
### What This Guide Does
|
|
|
|
This guide sets up **fully automated subscription management**:
|
|
|
|
1. User purchases subscription in Paymenter
|
|
2. Paymenter sends webhook to Discord bot
|
|
3. Discord bot assigns appropriate role to user
|
|
4. LuckPerms detects Discord role and syncs to in-game rank
|
|
5. Player automatically gets correct permissions on all 13 servers
|
|
|
|
**No manual work required after setup.**
|
|
|
|
### The Flow
|
|
|
|
```
|
|
User Subscribes ($1-$499)
|
|
↓
|
|
Paymenter (billing.firefrostgaming.com)
|
|
↓
|
|
Webhook fires (new purchase detected)
|
|
↓
|
|
Discord Bot receives webhook
|
|
↓
|
|
Bot assigns Discord role (The Awakened, Fire Elemental, etc.)
|
|
↓
|
|
LuckPerms syncs Discord role → In-game group
|
|
↓
|
|
Player gets permissions on all 13 servers instantly
|
|
↓
|
|
Player can join servers, claim chunks, set homes (based on tier)
|
|
```
|
|
|
|
### Time Estimate
|
|
|
|
- **Discord Bot Setup:** 1-2 hours (Michael + Holly)
|
|
- **Discord Roles:** 30 minutes (Holly)
|
|
- **LuckPerms Configuration:** 2-3 hours (Holly, across all 13 servers)
|
|
- **Paymenter Webhooks:** 1 hour (Michael + Holly testing)
|
|
|
|
**Total:** 4-6 hours
|
|
|
|
---
|
|
|
|
## 🏗️ ARCHITECTURE
|
|
|
|
### Components
|
|
|
|
1. **Paymenter** (billing.firefrostgaming.com) - Billing system
|
|
2. **Discord Server** - Community hub
|
|
3. **Discord Bot** - Automation middleman
|
|
4. **LuckPerms** - Permission management (all 13 game servers)
|
|
5. **MySQL Database** - Shared permission storage
|
|
|
|
### Why This Design?
|
|
|
|
**Why not direct Paymenter → LuckPerms?**
|
|
- Discord is the community hub - subscribers want Discord access too
|
|
- Discord roles provide social status and channel access
|
|
- Discord bot can handle complex logic (upgrades, downgrades, cancellations)
|
|
- Easier to troubleshoot (can see Discord roles visually)
|
|
|
|
**Why LuckPerms syncs FROM Discord?**
|
|
- Industry standard approach
|
|
- Discord becomes "source of truth" for subscriber status
|
|
- If someone loses subscriber role in Discord, they automatically lose in-game perks
|
|
- Prevents desync between Discord and game servers
|
|
|
|
---
|
|
|
|
## ✅ PREREQUISITES
|
|
|
|
### Before You Start
|
|
|
|
**Complete these first:**
|
|
|
|
- [ ] **Server-Side Mod Deployment Guide** completed on ALL 13 servers
|
|
- [ ] LuckPerms installed and connected to MySQL on all servers
|
|
- [ ] Michael has created MySQL database and provided credentials
|
|
- [ ] You have admin access to Firefrost Gaming Discord server
|
|
- [ ] You have access to Paymenter admin panel
|
|
|
|
### What You'll Need
|
|
|
|
**From Michael:**
|
|
- Discord bot token (Michael will create this)
|
|
- Paymenter admin credentials
|
|
- MySQL database credentials (already provided for LuckPerms)
|
|
|
|
**Access Required:**
|
|
- Discord server admin permissions
|
|
- Pterodactyl panel access (to restart servers)
|
|
- SSH access to game servers (for testing)
|
|
|
|
---
|
|
|
|
## 🤖 PART 1: DISCORD BOT SETUP
|
|
|
|
---
|
|
|
|
## 🔧 MICHAEL'S PRE-SETUP (Complete BEFORE Holly Starts)
|
|
|
|
**STOP: Michael must complete this entire section BEFORE handing the guide to Holly.**
|
|
|
|
### Task 1: Create Discord Application & Bot
|
|
|
|
**Michael's steps:**
|
|
|
|
1. Go to https://discord.com/developers/applications
|
|
2. Click **New Application**
|
|
3. Name: "Firefrost Subscription Manager"
|
|
4. Click **Create**
|
|
|
|
### Task 2: Configure Bot Settings
|
|
|
|
1. In the application, go to **Bot** tab (left sidebar)
|
|
2. Click **Add Bot** → **Yes, do it!**
|
|
3. Under **Privileged Gateway Intents**, enable:
|
|
- ✅ **Server Members Intent** (REQUIRED - bot needs to assign roles)
|
|
- ✅ **Message Content Intent** (REQUIRED - bot needs to read webhook data)
|
|
4. Click **Save Changes**
|
|
|
|
### Task 3: Get Bot Token
|
|
|
|
1. Under **Bot** tab, find **Token** section
|
|
2. Click **Reset Token** (confirm if asked)
|
|
3. Click **Copy** to copy the token
|
|
4. **SAVE THIS TOKEN SECURELY** - you'll give it to Holly later
|
|
|
|
**The token looks like:**
|
|
```
|
|
MTxxxxxxxxxxxxxxxxxxxxxx.xxxxxx.xxxxxxxxxxxxxxxxxxxxxxxxxxx
|
|
```
|
|
|
|
**⚠️ NEVER share this token publicly or commit it to git!**
|
|
|
|
### Task 4: Invite Bot to Discord Server
|
|
|
|
1. Go to **OAuth2** tab → **URL Generator** (left sidebar)
|
|
2. Under **Scopes**, select:
|
|
- ✅ `bot`
|
|
- ✅ `applications.commands`
|
|
3. Under **Bot Permissions**, select:
|
|
- ✅ **Manage Roles** (REQUIRED - assigns subscriber roles)
|
|
- ✅ **Send Messages** (for welcome DMs)
|
|
- ✅ **Read Message History** (optional)
|
|
- ✅ **Use Slash Commands** (future-proofing)
|
|
4. Scroll down and **Copy** the generated URL
|
|
5. Open the URL in a new browser tab
|
|
6. Select **Firefrost Gaming** server from dropdown
|
|
7. Click **Authorize**
|
|
8. Complete the CAPTCHA
|
|
|
|
**The bot should now appear in your Discord server's member list (offline status is normal - it's not running yet).**
|
|
|
|
### Task 5: Get Discord Server ID (Guild ID)
|
|
|
|
1. Open Discord
|
|
2. Go to **User Settings** (gear icon)
|
|
3. Go to **Advanced** (left sidebar)
|
|
4. Enable **Developer Mode** ✅
|
|
5. Close settings
|
|
6. Right-click your **Firefrost Gaming** server icon
|
|
7. Click **Copy Server ID**
|
|
8. **Save this ID** - you'll give it to Holly
|
|
|
|
**The ID looks like:**
|
|
```
|
|
123456789012345678
|
|
```
|
|
|
|
### Task 6: Deploy Bot Code on Command Center
|
|
|
|
**SSH to Command Center:**
|
|
|
|
```bash
|
|
ssh root@63.143.34.217
|
|
```
|
|
|
|
**Install Node.js (if not already installed):**
|
|
|
|
```bash
|
|
# Check if Node.js is installed
|
|
node --version
|
|
|
|
# If not installed or version < 18, install Node.js 20:
|
|
curl -fsSL https://deb.nodesource.com/setup_20.x | bash -
|
|
apt-get install -y nodejs
|
|
|
|
# Verify
|
|
node --version # Should show v20.x.x
|
|
npm --version # Should show 10.x.x
|
|
```
|
|
|
|
**Create bot directory:**
|
|
|
|
```bash
|
|
mkdir -p /opt/firefrost-discord-bot
|
|
cd /opt/firefrost-discord-bot
|
|
```
|
|
|
|
**Create package.json:**
|
|
|
|
```bash
|
|
cat > package.json << 'EOF'
|
|
{
|
|
"name": "firefrost-discord-bot",
|
|
"version": "1.0.0",
|
|
"description": "Firefrost Gaming subscription automation bot",
|
|
"main": "bot.js",
|
|
"scripts": {
|
|
"start": "node bot.js"
|
|
},
|
|
"dependencies": {
|
|
"discord.js": "^14.14.1",
|
|
"express": "^4.18.2",
|
|
"body-parser": "^1.20.2"
|
|
}
|
|
}
|
|
EOF
|
|
```
|
|
|
|
**Install dependencies:**
|
|
|
|
```bash
|
|
npm install
|
|
```
|
|
|
|
**Create bot.js file:**
|
|
|
|
```bash
|
|
cat > bot.js << 'EOF'
|
|
// Firefrost Gaming - Discord Subscription Bot
|
|
// Handles Paymenter webhooks and assigns Discord roles
|
|
|
|
const { Client, GatewayIntentBits } = require('discord.js');
|
|
const express = require('express');
|
|
const bodyParser = require('body-parser');
|
|
|
|
// Configuration - REPLACE THESE VALUES
|
|
const DISCORD_TOKEN = 'YOUR_BOT_TOKEN_HERE';
|
|
const GUILD_ID = 'YOUR_GUILD_ID_HERE';
|
|
|
|
// Product ID to Role ID mapping (from Paymenter)
|
|
// Holly will fill these in after creating Discord roles
|
|
const PRODUCT_ROLE_MAP = {
|
|
'2': 'AWAKENED_ROLE_ID',
|
|
'3': 'FIRE_ELEMENTAL_ROLE_ID',
|
|
'4': 'FROST_ELEMENTAL_ROLE_ID',
|
|
'5': 'FIRE_KNIGHT_ROLE_ID',
|
|
'6': 'FROST_KNIGHT_ROLE_ID',
|
|
'7': 'FIRE_MASTER_ROLE_ID',
|
|
'8': 'FROST_MASTER_ROLE_ID',
|
|
'9': 'FIRE_LEGEND_ROLE_ID',
|
|
'10': 'FROST_LEGEND_ROLE_ID',
|
|
'11': 'SOVEREIGN_ROLE_ID'
|
|
};
|
|
|
|
// Initialize Discord client
|
|
const client = new Client({
|
|
intents: [
|
|
GatewayIntentBits.Guilds,
|
|
GatewayIntentBits.GuildMembers
|
|
]
|
|
});
|
|
|
|
// Initialize Express for webhook receiver
|
|
const app = express();
|
|
app.use(bodyParser.json());
|
|
|
|
// Discord bot ready event
|
|
client.once('ready', () => {
|
|
console.log(`✅ Bot logged in as ${client.user.tag}`);
|
|
console.log(`🔗 Connected to ${client.guilds.cache.size} server(s)`);
|
|
});
|
|
|
|
// Webhook endpoint - Paymenter sends POST here
|
|
app.post('/webhook/paymenter', async (req, res) => {
|
|
try {
|
|
console.log('📬 Received webhook from Paymenter');
|
|
console.log('Payload:', JSON.stringify(req.body, null, 2));
|
|
|
|
const { event, product_id, user_email, discord_id } = req.body;
|
|
|
|
// Validate webhook
|
|
if (!event || !product_id) {
|
|
console.error('❌ Invalid webhook data - missing event or product_id');
|
|
return res.status(400).json({ error: 'Missing required fields' });
|
|
}
|
|
|
|
if (!discord_id) {
|
|
console.error('⚠️ No discord_id provided - cannot assign role');
|
|
return res.status(400).json({ error: 'Missing discord_id' });
|
|
}
|
|
|
|
console.log(`📦 Event: ${event}, Product: ${product_id}, Discord ID: ${discord_id}`);
|
|
|
|
// Get Discord guild
|
|
const guild = client.guilds.cache.get(GUILD_ID);
|
|
if (!guild) {
|
|
console.error('❌ Guild not found');
|
|
return res.status(500).json({ error: 'Guild not found' });
|
|
}
|
|
|
|
// Get member
|
|
const member = await guild.members.fetch(discord_id);
|
|
if (!member) {
|
|
console.error('❌ Member not found in Discord server');
|
|
return res.status(404).json({ error: 'Member not found' });
|
|
}
|
|
|
|
// Get role ID for this product
|
|
const roleId = PRODUCT_ROLE_MAP[product_id];
|
|
if (!roleId || roleId.includes('ROLE_ID')) {
|
|
console.error(`❌ No role mapped for product ${product_id} (or role ID not configured)`);
|
|
return res.status(400).json({ error: 'Unknown product or role not configured' });
|
|
}
|
|
|
|
// Handle event
|
|
if (event === 'subscription.created' || event === 'payment.completed') {
|
|
// Add role
|
|
await member.roles.add(roleId);
|
|
console.log(`✅ Added role ${roleId} to ${member.user.tag}`);
|
|
|
|
// Send welcome DM
|
|
try {
|
|
await member.send(`🎉 Welcome to Firefrost Gaming! Your subscription is now active. Check out the server - your perks are ready!`);
|
|
console.log(`📨 Sent welcome DM to ${member.user.tag}`);
|
|
} catch (err) {
|
|
console.log('⚠️ Could not send DM (user has DMs disabled)');
|
|
}
|
|
|
|
} else if (event === 'subscription.cancelled' || event === 'subscription.expired') {
|
|
// Remove role
|
|
await member.roles.remove(roleId);
|
|
console.log(`❌ Removed role ${roleId} from ${member.user.tag}`);
|
|
|
|
} else {
|
|
console.log(`⚠️ Unknown event type: ${event}`);
|
|
}
|
|
|
|
res.status(200).json({ success: true });
|
|
|
|
} catch (error) {
|
|
console.error('❌ Webhook processing error:', error);
|
|
res.status(500).json({ error: 'Internal server error', details: error.message });
|
|
}
|
|
});
|
|
|
|
// Health check endpoint
|
|
app.get('/health', (req, res) => {
|
|
res.status(200).json({
|
|
status: 'healthy',
|
|
bot: client.user ? client.user.tag : 'disconnected',
|
|
uptime: process.uptime()
|
|
});
|
|
});
|
|
|
|
// Start Express server
|
|
const PORT = 3100;
|
|
app.listen(PORT, () => {
|
|
console.log(`🌐 Webhook server listening on port ${PORT}`);
|
|
console.log(`📍 Webhook URL: http://localhost:${PORT}/webhook/paymenter`);
|
|
});
|
|
|
|
// Start Discord bot
|
|
client.login(DISCORD_TOKEN);
|
|
EOF
|
|
```
|
|
|
|
**Edit bot.js and add your credentials:**
|
|
|
|
```bash
|
|
nano bot.js
|
|
```
|
|
|
|
**Find these lines:**
|
|
```javascript
|
|
const DISCORD_TOKEN = 'YOUR_BOT_TOKEN_HERE';
|
|
const GUILD_ID = 'YOUR_GUILD_ID_HERE';
|
|
```
|
|
|
|
**Replace with:**
|
|
```javascript
|
|
const DISCORD_TOKEN = 'MTxxxx...'; // Your actual bot token from Task 3
|
|
const GUILD_ID = '123456789012345678'; // Your actual server ID from Task 5
|
|
```
|
|
|
|
**Save and exit** (Ctrl+X, Y, Enter)
|
|
|
|
**Create systemd service:**
|
|
|
|
```bash
|
|
cat > /etc/systemd/system/firefrost-discord-bot.service << 'EOF'
|
|
[Unit]
|
|
Description=Firefrost Gaming Discord Bot
|
|
After=network.target
|
|
|
|
[Service]
|
|
Type=simple
|
|
User=root
|
|
WorkingDirectory=/opt/firefrost-discord-bot
|
|
ExecStart=/usr/bin/node /opt/firefrost-discord-bot/bot.js
|
|
Restart=always
|
|
RestartSec=10
|
|
|
|
[Install]
|
|
WantedBy=multi-user.target
|
|
EOF
|
|
```
|
|
|
|
**Enable and start the bot:**
|
|
|
|
```bash
|
|
# Reload systemd
|
|
systemctl daemon-reload
|
|
|
|
# Enable auto-start on boot
|
|
systemctl enable firefrost-discord-bot
|
|
|
|
# Start the bot
|
|
systemctl start firefrost-discord-bot
|
|
|
|
# Check status
|
|
systemctl status firefrost-discord-bot
|
|
```
|
|
|
|
**You should see:**
|
|
```
|
|
● firefrost-discord-bot.service - Firefrost Gaming Discord Bot
|
|
Loaded: loaded
|
|
Active: active (running)
|
|
```
|
|
|
|
**View logs to confirm it's working:**
|
|
|
|
```bash
|
|
journalctl -u firefrost-discord-bot -f
|
|
```
|
|
|
|
**You should see:**
|
|
```
|
|
✅ Bot logged in as Firefrost Subscription Manager#1234
|
|
🔗 Connected to 1 server(s)
|
|
🌐 Webhook server listening on port 3100
|
|
```
|
|
|
|
**If you see errors about invalid token:**
|
|
- Double-check you copied the token correctly
|
|
- Make sure there are no extra spaces
|
|
- Verify the token hasn't been reset/revoked
|
|
|
|
**Press Ctrl+C to exit log view when done.**
|
|
|
|
### Task 7: Set Up DNS (Cloudflare)
|
|
|
|
**Before setting up Nginx, add DNS record:**
|
|
|
|
1. Go to https://dash.cloudflare.com
|
|
2. Select **firefrostgaming.com** domain
|
|
3. Go to **DNS** → **Records**
|
|
4. Click **Add record**
|
|
5. Configure:
|
|
- **Type:** A
|
|
- **Name:** webhook
|
|
- **IPv4 address:** 63.143.34.217 (Command Center IP)
|
|
- **Proxy status:** 🟠 DNS only (turn OFF the orange cloud)
|
|
- **TTL:** Auto
|
|
6. Click **Save**
|
|
|
|
**Wait 1-2 minutes for DNS to propagate.**
|
|
|
|
**Verify DNS is working:**
|
|
|
|
```bash
|
|
# Test DNS resolution
|
|
dig webhook.firefrostgaming.com
|
|
|
|
# Should show:
|
|
# webhook.firefrostgaming.com. 300 IN A 63.143.34.217
|
|
```
|
|
|
|
### Task 8: Set Up Nginx Reverse Proxy
|
|
|
|
**Still on Command Center, configure Nginx:**
|
|
|
|
```bash
|
|
cat > /etc/nginx/sites-available/discord-webhook << 'EOF'
|
|
server {
|
|
listen 80;
|
|
server_name webhook.firefrostgaming.com;
|
|
|
|
location / {
|
|
proxy_pass http://localhost:3100;
|
|
proxy_http_version 1.1;
|
|
proxy_set_header Upgrade $http_upgrade;
|
|
proxy_set_header Connection 'upgrade';
|
|
proxy_set_header Host $host;
|
|
proxy_set_header X-Real-IP $remote_addr;
|
|
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
|
proxy_cache_bypass $http_upgrade;
|
|
}
|
|
}
|
|
EOF
|
|
```
|
|
|
|
**Enable the site:**
|
|
|
|
```bash
|
|
ln -s /etc/nginx/sites-available/discord-webhook /etc/nginx/sites-enabled/
|
|
nginx -t
|
|
systemctl reload nginx
|
|
```
|
|
|
|
**Get SSL certificate:**
|
|
|
|
```bash
|
|
certbot --nginx -d webhook.firefrostgaming.com
|
|
```
|
|
|
|
**Test the webhook endpoint:**
|
|
|
|
```bash
|
|
curl https://webhook.firefrostgaming.com/health
|
|
```
|
|
|
|
**Should return:**
|
|
```json
|
|
{"status":"healthy","bot":"Firefrost Subscription Manager#1234","uptime":123.456}
|
|
```
|
|
|
|
### Task 9: Prepare Information for Holly
|
|
|
|
**Create a file with all the info Holly needs:**
|
|
|
|
```bash
|
|
cat > /root/holly-bot-credentials.txt << EOF
|
|
Firefrost Discord Bot - Credentials for Holly
|
|
|
|
Bot Name: Firefrost Subscription Manager
|
|
Bot Token: $(grep "const DISCORD_TOKEN" /opt/firefrost-discord-bot/bot.js | cut -d"'" -f2)
|
|
Guild ID: $(grep "const GUILD_ID" /opt/firefrost-discord-bot/bot.js | cut -d"'" -f2)
|
|
|
|
Webhook URL: https://webhook.firefrostgaming.com/webhook/paymenter
|
|
|
|
Bot is installed on: Command Center (63.143.34.217)
|
|
Bot directory: /opt/firefrost-discord-bot/
|
|
Service name: firefrost-discord-bot
|
|
|
|
Commands for Holly:
|
|
- View logs: journalctl -u firefrost-discord-bot -f
|
|
- Restart bot: systemctl restart firefrost-discord-bot
|
|
- Edit bot code: nano /opt/firefrost-discord-bot/bot.js
|
|
|
|
Next Steps:
|
|
1. Holly creates Discord roles (Part 2 of guide)
|
|
2. Holly gets role IDs and updates bot.js PRODUCT_ROLE_MAP
|
|
3. Holly restarts bot: systemctl restart firefrost-discord-bot
|
|
4. Test webhook flow
|
|
|
|
---
|
|
Generated: $(date)
|
|
EOF
|
|
|
|
cat /root/holly-bot-credentials.txt
|
|
```
|
|
|
|
**Save this output - you'll give it to Holly.**
|
|
|
|
---
|
|
|
|
## ✅ MICHAEL'S PRE-SETUP COMPLETE
|
|
|
|
**Checklist before handing to Holly:**
|
|
|
|
- [ ] Discord bot created and invited to server
|
|
- [ ] Bot token saved securely
|
|
- [ ] Guild ID recorded
|
|
- [ ] Node.js installed on Command Center
|
|
- [ ] Bot code deployed to /opt/firefrost-discord-bot/
|
|
- [ ] Bot service running successfully
|
|
- [ ] Nginx reverse proxy configured
|
|
- [ ] SSL certificate obtained
|
|
- [ ] Webhook endpoint accessible at https://webhook.firefrostgaming.com
|
|
- [ ] Credentials file created for Holly
|
|
|
|
**If all checked, proceed to Part 2 and hand the guide to Holly.**
|
|
|
|
---
|
|
|
|
## 👥 HOLLY'S TASKS START HERE
|
|
|
|
**At this point, Michael has:**
|
|
- ✅ Created the Discord bot application
|
|
- ✅ Deployed bot code to Command Center
|
|
- ✅ Set up Nginx reverse proxy
|
|
- ✅ Bot is running and accessible at https://webhook.firefrostgaming.com
|
|
|
|
**Holly, you now need to:**
|
|
1. Create Discord roles (Part 2)
|
|
2. Update bot code with role IDs
|
|
3. Configure LuckPerms
|
|
4. Test the complete flow
|
|
|
|
---
|
|
|
|
## 👥 PART 2: DISCORD ROLES CONFIGURATION
|
|
|
|
### Step 1: Create Discord Roles (Holly's Task)
|
|
|
|
**In your Discord server:**
|
|
|
|
1. Right-click server icon → **Server Settings**
|
|
2. Click **Roles**
|
|
3. Click **Create Role** for each tier
|
|
|
|
**Create these roles (in order, top to bottom):**
|
|
|
|
#### Role 1: Sovereign (Founder)
|
|
- **Name:** `⚡ Sovereign`
|
|
- **Color:** `#FFD600` (Amber Gold)
|
|
- **Permissions:** (default member permissions)
|
|
- **Display separately:** ✅ Yes
|
|
- **Mentionable:** ✅ Yes
|
|
|
|
#### Role 2: Fire Legend
|
|
- **Name:** `🔥 Fire Legend`
|
|
- **Color:** `#FF3D00` (Deep Orange/Red)
|
|
- **Permissions:** (default member permissions)
|
|
- **Display separately:** ✅ Yes
|
|
|
|
#### Role 3: Frost Legend
|
|
- **Name:** `❄️ Frost Legend`
|
|
- **Color:** `#00E5FF` (Electric Cyan)
|
|
- **Permissions:** (default member permissions)
|
|
- **Display separately:** ✅ Yes
|
|
|
|
#### Role 4: Fire Master
|
|
- **Name:** `🔥 Fire Master`
|
|
- **Color:** `#FF3D00`
|
|
- **Permissions:** (default member permissions)
|
|
- **Display separately:** ✅ Yes
|
|
|
|
#### Role 5: Frost Master
|
|
- **Name:** `❄️ Frost Master`
|
|
- **Color:** `#00E5FF`
|
|
- **Permissions:** (default member permissions)
|
|
- **Display separately:** ✅ Yes
|
|
|
|
#### Role 6: Fire Knight
|
|
- **Name:** `🔥 Fire Knight`
|
|
- **Color:** `#FF3D00`
|
|
- **Permissions:** (default member permissions)
|
|
- **Display separately:** ✅ Yes
|
|
|
|
#### Role 7: Frost Knight
|
|
- **Name:** `❄️ Frost Knight`
|
|
- **Color:** `#00E5FF`
|
|
- **Permissions:** (default member permissions)
|
|
- **Display separately:** ✅ Yes
|
|
|
|
#### Role 8: Fire Elemental
|
|
- **Name:** `🔥 Fire Elemental`
|
|
- **Color:** `#FF3D00`
|
|
- **Permissions:** (default member permissions)
|
|
- **Display separately:** ✅ Yes
|
|
|
|
#### Role 9: Frost Elemental
|
|
- **Name:** `❄️ Frost Elemental`
|
|
- **Color:** `#00E5FF`
|
|
- **Permissions:** (default member permissions)
|
|
- **Display separately:** ✅ Yes
|
|
|
|
#### Role 10: The Awakened
|
|
- **Name:** `The Awakened`
|
|
- **Color:** `#FFFFFF` (White)
|
|
- **Permissions:** (default member permissions)
|
|
- **Display separately:** ✅ Yes
|
|
|
|
#### Role 11: Wanderer (Free)
|
|
- **Name:** `Wanderer`
|
|
- **Color:** `#99AAB5` (Gray)
|
|
- **Permissions:** Read messages only (restrict Send Messages in channels)
|
|
- **Display separately:** No
|
|
|
|
### Step 2: Get Role IDs
|
|
|
|
**For each role you just created:**
|
|
|
|
1. Right-click the role in Server Settings → Roles
|
|
2. Click **Copy ID** (if you don't see this, enable Developer Mode in Discord settings)
|
|
3. Paste the ID somewhere - you'll need them
|
|
|
|
**Create a mapping:**
|
|
```
|
|
The Awakened: 123456789012345678
|
|
Fire Elemental: 234567890123456789
|
|
Frost Elemental: 345678901234567890
|
|
Fire Knight: 456789012345678901
|
|
Frost Knight: 567890123456789012
|
|
Fire Master: 678901234567890123
|
|
Frost Master: 789012345678901234
|
|
Fire Legend: 890123456789012345
|
|
Frost Legend: 901234567890123456
|
|
Sovereign: 012345678901234567
|
|
```
|
|
|
|
### Step 3: Update Bot Code with Role IDs (Michael's Task)
|
|
|
|
**Holly:** After you create all the Discord roles and copy their IDs (from Step 2), give the list to Michael. He'll update the bot code.
|
|
|
|
**Michael:** Holly will give you a list like this:
|
|
```
|
|
The Awakened: 123456789012345678
|
|
Fire Elemental: 234567890123456789
|
|
Frost Elemental: 345678901234567890
|
|
Fire Knight: 456789012345678901
|
|
Frost Knight: 567890123456789012
|
|
Fire Master: 678901234567890123
|
|
Frost Master: 789012345678901234
|
|
Fire Legend: 890123456789012345
|
|
Frost Legend: 901234567890123456
|
|
Sovereign: 012345678901234567
|
|
```
|
|
|
|
**SSH to Command Center and edit the bot code:**
|
|
|
|
```bash
|
|
ssh root@63.143.34.217
|
|
nano /opt/firefrost-discord-bot/bot.js
|
|
```
|
|
|
|
**Find the `PRODUCT_ROLE_MAP` section and replace it:**
|
|
|
|
```javascript
|
|
const PRODUCT_ROLE_MAP = {
|
|
'2': '123456789012345678', // The Awakened (use Holly's actual ID)
|
|
'3': '234567890123456789', // Fire Elemental
|
|
'4': '345678901234567890', // Frost Elemental
|
|
'5': '456789012345678901', // Fire Knight
|
|
'6': '567890123456789012', // Frost Knight
|
|
'7': '678901234567890123', // Fire Master
|
|
'8': '789012345678901234', // Frost Master
|
|
'9': '890123456789012345', // Fire Legend
|
|
'10': '901234567890123456', // Frost Legend
|
|
'11': '012345678901234567' // Sovereign
|
|
};
|
|
```
|
|
|
|
**Save and exit** (Ctrl+X, Y, Enter)
|
|
|
|
**Restart the bot:**
|
|
|
|
```bash
|
|
systemctl restart firefrost-discord-bot
|
|
|
|
# Verify it restarted successfully
|
|
systemctl status firefrost-discord-bot
|
|
|
|
# Check logs to confirm no errors
|
|
journalctl -u firefrost-discord-bot -f
|
|
```
|
|
|
|
**You should see:**
|
|
```
|
|
✅ Bot logged in as Firefrost Subscription Manager#1234
|
|
🌐 Webhook server listening on port 3100
|
|
```
|
|
|
|
**Now hand back to Holly for Part 3.**
|
|
|
|
### Step 4: Configure Channel Permissions
|
|
|
|
**Create private channels for Fire/Frost paths:**
|
|
|
|
#### Fire Path Channels
|
|
- `#🔥-fire-general` - Only visible to Fire Elemental+ roles
|
|
- `#🔥-fire-builds` - Only visible to Fire Elemental+ roles
|
|
- `#🔥-fire-strategy` - Only visible to Fire Elemental+ roles
|
|
|
|
**Permissions:**
|
|
- Deny: `@everyone` - View Channel
|
|
- Allow: `@🔥 Fire Elemental`, `@🔥 Fire Knight`, `@🔥 Fire Master`, `@🔥 Fire Legend`, `@⚡ Sovereign`
|
|
|
|
#### Frost Path Channels
|
|
- `#❄️-frost-general` - Only visible to Frost Elemental+ roles
|
|
- `#❄️-frost-builds` - Only visible to Frost Elemental+ roles
|
|
- `#❄️-frost-strategy` - Only visible to Frost Elemental+ roles
|
|
|
|
**Permissions:**
|
|
- Deny: `@everyone` - View Channel
|
|
- Allow: `@❄️ Frost Elemental`, `@❄️ Frost Knight`, `@❄️ Frost Master`, `@❄️ Frost Legend`, `@⚡ Sovereign`
|
|
|
|
#### The Nexus (Sovereign Only)
|
|
- `#⚡-the-nexus` - Only visible to Sovereign
|
|
|
|
**Permissions:**
|
|
- Deny: `@everyone` - View Channel
|
|
- Allow: `@⚡ Sovereign` only
|
|
|
|
---
|
|
|
|
## ⚙️ PART 3: LUCKPERMS GROUPS & PERMISSIONS
|
|
|
|
**This is the longest section - you'll configure 11 groups across 13 servers.**
|
|
|
|
### Step 1: Create LuckPerms Groups
|
|
|
|
**Access ONE game server's console first (we'll sync to others after):**
|
|
|
|
1. Go to https://panel.firefrostgaming.com
|
|
2. Click on any server (doesn't matter which - they all share the MySQL database)
|
|
3. Click **Console** tab
|
|
4. Make sure server is **running** (start it if stopped)
|
|
|
|
**Then run these commands in the console:**
|
|
|
|
#### Create Wanderer Group (Free Tier)
|
|
|
|
```
|
|
/lp creategroup wanderer
|
|
/lp group wanderer setweight 10
|
|
/lp group wanderer meta setprefix "&7[Wanderer] "
|
|
/lp group wanderer meta setsuffix ""
|
|
```
|
|
|
|
#### Create Awakened Group ($1 Tier)
|
|
|
|
```
|
|
/lp creategroup awakened
|
|
/lp group awakened parent add wanderer
|
|
/lp group awakened setweight 20
|
|
/lp group awakened meta setprefix "&f[The Awakened] "
|
|
|
|
# Permissions
|
|
/lp group awakened permission set ftbessentials.home.set true
|
|
/lp group awakened permission set ftbessentials.home.teleport true
|
|
/lp group awakened meta setmeta max-homes 1
|
|
```
|
|
|
|
#### Create Fire Elemental Group ($5/mo)
|
|
|
|
```
|
|
/lp creategroup fire_elemental
|
|
/lp group fire_elemental parent add awakened
|
|
/lp group fire_elemental setweight 30
|
|
/lp group fire_elemental meta setprefix "&c[🔥 Fire Elemental] "
|
|
|
|
# Permissions
|
|
/lp group fire_elemental meta setmeta max-homes 5
|
|
/lp group fire_elemental permission set ftbchunks.claim true
|
|
/lp group fire_elemental meta setmeta max-claimed-chunks 25
|
|
/lp group fire_elemental permission set ftbessentials.rtp true
|
|
/lp group fire_elemental meta setmeta rtp-cooldown 3600
|
|
```
|
|
|
|
#### Create Frost Elemental Group ($5/mo)
|
|
|
|
```
|
|
/lp creategroup frost_elemental
|
|
/lp group frost_elemental parent add awakened
|
|
/lp group frost_elemental setweight 30
|
|
/lp group frost_elemental meta setprefix "&b[❄️ Frost Elemental] "
|
|
|
|
# Permissions (same as Fire Elemental)
|
|
/lp group frost_elemental meta setmeta max-homes 5
|
|
/lp group frost_elemental permission set ftbchunks.claim true
|
|
/lp group frost_elemental meta setmeta max-claimed-chunks 25
|
|
/lp group frost_elemental permission set ftbessentials.rtp true
|
|
/lp group frost_elemental meta setmeta rtp-cooldown 3600
|
|
```
|
|
|
|
#### Create Fire Knight Group ($10/mo)
|
|
|
|
```
|
|
/lp creategroup fire_knight
|
|
/lp group fire_knight parent add fire_elemental
|
|
/lp group fire_knight setweight 40
|
|
/lp group fire_knight meta setprefix "&c[🔥 Fire Knight] "
|
|
|
|
# Permissions
|
|
/lp group fire_knight meta setmeta max-homes 10
|
|
/lp group fire_knight meta setmeta max-claimed-chunks 49
|
|
/lp group fire_knight meta setmeta max-force-loaded-chunks 4
|
|
/lp group fire_knight meta setmeta rtp-cooldown 1800
|
|
```
|
|
|
|
#### Create Frost Knight Group ($10/mo)
|
|
|
|
```
|
|
/lp creategroup frost_knight
|
|
/lp group frost_knight parent add frost_elemental
|
|
/lp group frost_knight setweight 40
|
|
/lp group frost_knight meta setprefix "&b[❄️ Frost Knight] "
|
|
|
|
# Permissions (same as Fire Knight)
|
|
/lp group frost_knight meta setmeta max-homes 10
|
|
/lp group frost_knight meta setmeta max-claimed-chunks 49
|
|
/lp group frost_knight meta setmeta max-force-loaded-chunks 4
|
|
/lp group frost_knight meta setmeta rtp-cooldown 1800
|
|
```
|
|
|
|
#### Create Fire Master Group ($15/mo)
|
|
|
|
```
|
|
/lp creategroup fire_master
|
|
/lp group fire_master parent add fire_knight
|
|
/lp group fire_master setweight 50
|
|
/lp group fire_master meta setprefix "&c[🔥 Fire Master] "
|
|
|
|
# Permissions
|
|
/lp group fire_master meta setmeta max-homes 20
|
|
/lp group fire_master meta setmeta max-claimed-chunks 100
|
|
/lp group fire_master meta setmeta max-force-loaded-chunks 9
|
|
/lp group fire_master meta setmeta rtp-cooldown 900
|
|
```
|
|
|
|
#### Create Frost Master Group ($15/mo)
|
|
|
|
```
|
|
/lp creategroup frost_master
|
|
/lp group frost_master parent add frost_knight
|
|
/lp group frost_master setweight 50
|
|
/lp group frost_master meta setprefix "&b[❄️ Frost Master] "
|
|
|
|
# Permissions
|
|
/lp group frost_master meta setmeta max-homes 20
|
|
/lp group frost_master meta setmeta max-claimed-chunks 100
|
|
/lp group frost_master meta setmeta max-force-loaded-chunks 9
|
|
/lp group frost_master meta setmeta rtp-cooldown 900
|
|
```
|
|
|
|
#### Create Fire Legend Group ($20/mo)
|
|
|
|
```
|
|
/lp creategroup fire_legend
|
|
/lp group fire_legend parent add fire_master
|
|
/lp group fire_legend setweight 60
|
|
/lp group fire_legend meta setprefix "&c[🔥 Fire Legend] "
|
|
|
|
# Permissions
|
|
/lp group fire_legend meta setmeta max-homes 35
|
|
/lp group fire_legend meta setmeta max-claimed-chunks 121
|
|
/lp group fire_legend meta setmeta max-force-loaded-chunks 16
|
|
/lp group fire_legend meta setmeta rtp-cooldown 600
|
|
```
|
|
|
|
#### Create Frost Legend Group ($20/mo)
|
|
|
|
```
|
|
/lp creategroup frost_legend
|
|
/lp group frost_legend parent add frost_master
|
|
/lp group frost_legend setweight 60
|
|
/lp group frost_legend meta setprefix "&b[❄️ Frost Legend] "
|
|
|
|
# Permissions
|
|
/lp group frost_legend meta setmeta max-homes 35
|
|
/lp group frost_legend meta setmeta max-claimed-chunks 121
|
|
/lp group frost_legend meta setmeta max-force-loaded-chunks 16
|
|
/lp group frost_legend meta setmeta rtp-cooldown 600
|
|
```
|
|
|
|
#### Create Sovereign (Founder) Group ($499 Lifetime)
|
|
|
|
```
|
|
/lp creategroup sovereign
|
|
/lp group sovereign parent add awakened
|
|
/lp group sovereign setweight 100
|
|
/lp group sovereign meta setprefix "&6[⚡ Founder] "
|
|
|
|
# Permissions (maximum everything)
|
|
/lp group sovereign meta setmeta max-homes 50
|
|
/lp group sovereign meta setmeta max-claimed-chunks 225
|
|
/lp group sovereign meta setmeta max-force-loaded-chunks 81
|
|
/lp group sovereign permission set ftbessentials.rtp true
|
|
# No rtp cooldown for Sovereign
|
|
```
|
|
|
|
### Step 2: Verify Groups Created
|
|
|
|
```
|
|
/lp listgroups
|
|
```
|
|
|
|
**You should see all 11 groups listed.**
|
|
|
|
### Step 3: Sync to All Other Servers
|
|
|
|
**Because all servers connect to the SAME MySQL database, the groups are already synced!**
|
|
|
|
**To verify on another server:**
|
|
|
|
1. Go to Pterodactyl Panel
|
|
2. Open console for a different server
|
|
3. Run `/lp listgroups`
|
|
4. Should show the same 11 groups
|
|
|
|
**If groups don't appear:**
|
|
- Check that server's LuckPerms config points to the MySQL database
|
|
- Restart the server
|
|
|
|
---
|
|
|
|
## 🔗 PART 4: LUCKPERMS DISCORD INTEGRATION
|
|
|
|
**This connects Discord roles to LuckPerms groups.**
|
|
|
|
### Step 1: Enable Discord Integration in LuckPerms
|
|
|
|
**On EVERY server, edit `/config/luckperms/luckperms.conf`:**
|
|
|
|
**Find the section:**
|
|
```conf
|
|
# Discord integration
|
|
discord-integration {
|
|
enabled = false
|
|
}
|
|
```
|
|
|
|
**Change to:**
|
|
```conf
|
|
discord-integration {
|
|
enabled = true
|
|
|
|
# Role to group mappings
|
|
role-mappings {
|
|
# Format: "discord-role-id" = "luckperms-group"
|
|
|
|
"123456789012345678" = "awakened" # The Awakened
|
|
"234567890123456789" = "fire_elemental" # Fire Elemental
|
|
"345678901234567890" = "frost_elemental" # Frost Elemental
|
|
"456789012345678901" = "fire_knight" # Fire Knight
|
|
"567890123456789012" = "frost_knight" # Frost Knight
|
|
"678901234567890123" = "fire_master" # Fire Master
|
|
"789012345678901234" = "frost_master" # Frost Master
|
|
"890123456789012345" = "fire_legend" # Fire Legend
|
|
"901234567890123456" = "frost_legend" # Frost Legend
|
|
"012345678901234567" = "sovereign" # Sovereign
|
|
}
|
|
}
|
|
```
|
|
|
|
**Replace role IDs with the ACTUAL role IDs you copied in Part 2.**
|
|
|
|
**Save the file.**
|
|
|
|
### Step 2: Restart All Servers
|
|
|
|
**Via Pterodactyl Panel:**
|
|
|
|
1. Open each server's console
|
|
2. Click **Restart**
|
|
3. Wait for server to come back online
|
|
|
|
**Repeat for all 13 servers.**
|
|
|
|
### Step 3: Test Discord → LuckPerms Sync
|
|
|
|
**Manual test:**
|
|
|
|
1. Go to Discord
|
|
2. Manually assign yourself `The Awakened` role (right-click your name → Roles)
|
|
3. Join a Minecraft server
|
|
4. Run `/lp user YourUsername info`
|
|
5. Should show you're in the `awakened` group
|
|
|
|
**If it doesn't work:**
|
|
- Check LuckPerms config for typos in role IDs
|
|
- Check that Discord integration is enabled
|
|
- Restart the server
|
|
|
|
---
|
|
|
|
## 🪝 PART 5: PAYMENTER WEBHOOK CONFIGURATION
|
|
|
|
**This connects Paymenter to the Discord bot.**
|
|
|
|
### Step 1: Set Up Nginx Proxy (Michael's Task)
|
|
|
|
**On Command Center (where Discord bot runs):**
|
|
|
|
**Create file: `/etc/nginx/sites-available/discord-bot-webhook`**
|
|
|
|
```nginx
|
|
server {
|
|
listen 80;
|
|
server_name webhook.firefrostgaming.com;
|
|
|
|
location / {
|
|
proxy_pass http://localhost:3100;
|
|
proxy_http_version 1.1;
|
|
proxy_set_header Upgrade $http_upgrade;
|
|
proxy_set_header Connection 'upgrade';
|
|
proxy_set_header Host $host;
|
|
proxy_cache_bypass $http_upgrade;
|
|
}
|
|
}
|
|
```
|
|
|
|
**Enable the site:**
|
|
|
|
```bash
|
|
ln -s /etc/nginx/sites-available/discord-bot-webhook /etc/nginx/sites-enabled/
|
|
nginx -t
|
|
systemctl reload nginx
|
|
```
|
|
|
|
**Get SSL certificate:**
|
|
|
|
```bash
|
|
certbot --nginx -d webhook.firefrostgaming.com
|
|
```
|
|
|
|
**Now the webhook endpoint is:**
|
|
```
|
|
https://webhook.firefrostgaming.com/webhook/paymenter
|
|
```
|
|
|
|
### Step 2: Configure Paymenter Webhooks (Michael + Holly)
|
|
|
|
**In Paymenter admin panel:**
|
|
|
|
1. Go to **Settings** → **Webhooks**
|
|
2. Click **Add Webhook**
|
|
3. Configure:
|
|
- **URL:** `https://webhook.firefrostgaming.com/webhook/paymenter`
|
|
- **Events:**
|
|
- ✅ `subscription.created`
|
|
- ✅ `payment.completed`
|
|
- ✅ `subscription.cancelled`
|
|
- ✅ `subscription.expired`
|
|
- **Payload Format:** JSON
|
|
4. Click **Save**
|
|
|
|
### Step 3: Test Webhook
|
|
|
|
**Create a test purchase in Paymenter (use test mode if available).**
|
|
|
|
**Watch Discord bot logs:**
|
|
|
|
```bash
|
|
journalctl -u firefrost-discord-bot -f
|
|
```
|
|
|
|
**You should see:**
|
|
```
|
|
📬 Received webhook from Paymenter
|
|
📦 Event: subscription.created, Product: 2, User: 123456789012345678
|
|
✅ Added role 123456789012345678 to TestUser#1234
|
|
```
|
|
|
|
**If it works, the user should now have The Awakened role in Discord.**
|
|
|
|
**If it doesn't work:**
|
|
- Check webhook URL is correct
|
|
- Check Paymenter is sending the correct payload format
|
|
- Check Discord bot logs for errors
|
|
|
|
---
|
|
|
|
## ✅ TESTING & VERIFICATION
|
|
|
|
### End-to-End Test
|
|
|
|
**Complete flow test:**
|
|
|
|
1. **Create test user in Discord**
|
|
2. **Purchase Awakened tier ($1) in Paymenter**
|
|
3. **Verify webhook fires** (check Discord bot logs)
|
|
4. **Verify Discord role assigned** (check Discord - user should have "The Awakened" role)
|
|
5. **Join Minecraft server**
|
|
6. **Run `/lp user TestUser info`** - Should show `awakened` group
|
|
7. **Test permissions:**
|
|
- `/sethome test` - Should work (1 home allowed)
|
|
- `/sethome test2` - Should FAIL (only 1 home for Awakened)
|
|
- Try claiming chunks - Should FAIL (Awakened has 0 chunk claims)
|
|
- Try `/rtp` - Should FAIL (Awakened has no /rtp access)
|
|
|
|
**If all these work correctly, the automation is functioning!**
|
|
|
|
### Upgrade Test
|
|
|
|
**Test tier upgrade:**
|
|
|
|
1. Upgrade test user to Fire Elemental ($5/mo) in Paymenter
|
|
2. Verify Discord role changes (old role removed, new role added)
|
|
3. Join Minecraft server
|
|
4. Run `/lp user TestUser info` - Should show `fire_elemental` group
|
|
5. Test new permissions:
|
|
- `/sethome` - Should work (5 homes allowed)
|
|
- Claim chunks - Should work (25 chunks allowed)
|
|
- `/rtp` - Should work (60 minute cooldown)
|
|
|
|
### Cancellation Test
|
|
|
|
**Test subscription cancellation:**
|
|
|
|
1. Cancel test user's subscription in Paymenter
|
|
2. Verify Discord role removed
|
|
3. Join Minecraft server
|
|
4. Run `/lp user TestUser info` - Should show `wanderer` or default group
|
|
5. Test permissions:
|
|
- `/sethome` - Should FAIL (no subscription)
|
|
- Try joining server - Should be DENIED (whitelist = Awakened+ only)
|
|
|
|
---
|
|
|
|
## 🔧 TROUBLESHOOTING
|
|
|
|
### Discord Role Not Assigned After Purchase
|
|
|
|
**Symptoms:** User purchases subscription but doesn't get Discord role.
|
|
|
|
**Check:**
|
|
1. **Webhook logs:** `journalctl -u firefrost-discord-bot -f`
|
|
- Are webhooks being received?
|
|
2. **Paymenter webhook config:** Is webhook URL correct?
|
|
3. **Discord bot permissions:** Does bot have "Manage Roles" permission?
|
|
4. **Role position:** Bot's role must be ABOVE subscriber roles in Discord role hierarchy
|
|
|
|
**Solution:**
|
|
- Move bot's role to the top of the role list in Discord Server Settings
|
|
- Restart Discord bot: `systemctl restart firefrost-discord-bot`
|
|
|
|
---
|
|
|
|
### LuckPerms Not Syncing Discord Roles
|
|
|
|
**Symptoms:** User has Discord role but no in-game permissions.
|
|
|
|
**Check:**
|
|
1. **LuckPerms config:** Is Discord integration enabled?
|
|
2. **Role IDs:** Are Discord role IDs correct in luckperms.conf?
|
|
3. **Server restart:** Did you restart server after config change?
|
|
|
|
**Solution:**
|
|
- Double-check role IDs match (right-click role in Discord → Copy ID)
|
|
- Ensure luckperms.conf has correct mapping
|
|
- Restart all game servers
|
|
|
|
---
|
|
|
|
### User Can't Join Server After Subscribing
|
|
|
|
**Symptoms:** User purchased subscription, has Discord role, but can't join server.
|
|
|
|
**Check:**
|
|
1. **Whitelist status:** Is whitelist enabled on server?
|
|
2. **LuckPerms sync:** Run `/whitelist add Username` manually as test
|
|
3. **Server online:** Is server actually running?
|
|
|
|
**Solution:**
|
|
- Ensure LuckPerms-based whitelist is configured (see Server-Side Mod Deployment Guide)
|
|
- Check server console for "User not whitelisted" messages
|
|
- Manually add to whitelist temporarily while debugging
|
|
|
|
---
|
|
|
|
### Webhook Endpoint Returns 500 Error
|
|
|
|
**Symptoms:** Paymenter shows webhook failed with 500 error.
|
|
|
|
**Check:**
|
|
1. **Bot running:** `systemctl status firefrost-discord-bot`
|
|
2. **Bot logs:** `journalctl -u firefrost-discord-bot -f` for errors
|
|
3. **Nginx proxy:** Is Nginx running and proxying correctly?
|
|
|
|
**Solution:**
|
|
- Restart Discord bot
|
|
- Check bot code for syntax errors
|
|
- Test webhook manually with curl:
|
|
```bash
|
|
curl -X POST https://webhook.firefrostgaming.com/webhook/paymenter \
|
|
-H "Content-Type: application/json" \
|
|
-d '{"event":"subscription.created","product_id":"2","discord_id":"YOUR_DISCORD_ID"}'
|
|
```
|
|
|
|
---
|
|
|
|
## 📚 REFERENCE
|
|
|
|
### Quick Command Reference
|
|
|
|
#### Discord Bot Management
|
|
|
|
```bash
|
|
# Start bot
|
|
systemctl start firefrost-discord-bot
|
|
|
|
# Stop bot
|
|
systemctl stop firefrost-discord-bot
|
|
|
|
# Restart bot
|
|
systemctl restart firefrost-discord-bot
|
|
|
|
# View logs
|
|
journalctl -u firefrost-discord-bot -f
|
|
|
|
# Check status
|
|
systemctl status firefrost-discord-bot
|
|
```
|
|
|
|
#### LuckPerms Commands
|
|
|
|
```bash
|
|
# View user's groups
|
|
/lp user <username> info
|
|
|
|
# Manually add user to group
|
|
/lp user <username> parent add <groupname>
|
|
|
|
# Remove user from group
|
|
/lp user <username> parent remove <groupname>
|
|
|
|
# View group permissions
|
|
/lp group <groupname> permission info
|
|
|
|
# List all groups
|
|
/lp listgroups
|
|
```
|
|
|
|
---
|
|
|
|
### Subscriber Tier → Discord Role → LuckPerms Group Mapping
|
|
|
|
| Tier | Price | Discord Role | LuckPerms Group |
|
|
|------|-------|--------------|-----------------|
|
|
| Wanderer | Free | `Wanderer` | `wanderer` |
|
|
| Awakened | $1 | `The Awakened` | `awakened` |
|
|
| Fire Elemental | $5/mo | `🔥 Fire Elemental` | `fire_elemental` |
|
|
| Frost Elemental | $5/mo | `❄️ Frost Elemental` | `frost_elemental` |
|
|
| Fire Knight | $10/mo | `🔥 Fire Knight` | `fire_knight` |
|
|
| Frost Knight | $10/mo | `❄️ Frost Knight` | `frost_knight` |
|
|
| Fire Master | $15/mo | `🔥 Fire Master` | `fire_master` |
|
|
| Frost Master | $15/mo | `❄️ Frost Master` | `frost_master` |
|
|
| Fire Legend | $20/mo | `🔥 Fire Legend` | `fire_legend` |
|
|
| Frost Legend | $20/mo | `❄️ Frost Legend` | `frost_legend` |
|
|
| Sovereign | $499 | `⚡ Sovereign` | `sovereign` |
|
|
|
|
---
|
|
|
|
### File Locations Quick Reference
|
|
|
|
```
|
|
Command Center (63.143.34.217)
|
|
└── /opt/firefrost-discord-bot/
|
|
├── bot.js
|
|
├── package.json
|
|
└── node_modules/
|
|
|
|
Game Servers (TX1/NC1)
|
|
└── /config/luckperms/
|
|
└── luckperms.conf (Discord integration config)
|
|
|
|
Nginx
|
|
└── /etc/nginx/sites-available/
|
|
└── discord-bot-webhook
|
|
```
|
|
|
|
---
|
|
|
|
**End of Subscription Automation Guide**
|
|
|
|
**You've now completed the full automation setup! Users can subscribe in Paymenter and automatically get:**
|
|
- Discord role assignment
|
|
- In-game rank sync
|
|
- Correct permissions on all 13 servers
|
|
- Channel access based on Fire/Frost path
|
|
|
|
**Fire + Frost + Foundation = Where Love Builds Legacy** 🔥❄️
|
|
|
|
---
|
|
|
|
**Document Version:** 1.0
|
|
**Last Updated:** March 23, 2026
|
|
**Maintained By:** Firefrost Gaming Infrastructure Team
|