DayZ
Overview
Reward your DayZ server players for voting on topgservers. DayZ modding uses Enforce Script (a C-like language), but HTTP calls require an external sidecar. This guide covers a Python vote-checker that writes results to a JSON file, which an Enforce Script mod reads to grant in-game items.
Prerequisites
- A DayZ server with mod support (Community Framework recommended)
- Python 3.8+ on the server machine for the vote-check sidecar
- A topgservers API key — generate one in My Servers → API
- Your webhook secret (optional, for real-time rewards)
- Basic familiarity with DayZ modding and Enforce Script
Installation
1 Create the mod structure
Set up a standard DayZ mod with the vote reward script and the external Python sidecar.
@TopGVote/
├── Addons/
│ └── TopGVote/
│ ├── config.cpp
│ └── Scripts/
│ └── 4_World/
│ └── TopGVoteReward.c
├── topg_checker.py (runs alongside server)
└── votes.json (bridge file) 2 Create the Python vote checker sidecar
This script runs alongside your DayZ server. It polls the topgservers API for online players and writes results to a JSON file that the Enforce Script mod reads.
#!/usr/bin/env python3
"""
topgservers vote checker sidecar for DayZ.
Run alongside DayZ server: python3 topg_checker.py
Writes vote results to votes.json for the Enforce Script mod.
"""
import requests
import json
import time
import os
API_KEY = "tgs_your_api_key_here"
CHECK_INTERVAL = 60 # seconds
VOTES_FILE = "votes.json"
PLAYERS_FILE = "online_players.txt" # Written by server mod
def load_online_players():
"""Read online player list written by the DayZ mod."""
if not os.path.exists(PLAYERS_FILE):
return []
with open(PLAYERS_FILE, 'r') as f:
return [line.strip() for line in f if line.strip()]
def check_votes():
"""Check vote status for all online players."""
players = load_online_players()
votes = {}
# Load existing votes
if os.path.exists(VOTES_FILE):
with open(VOTES_FILE, 'r') as f:
votes = json.load(f)
for name in players:
if name in votes and votes[name].get("rewarded"):
continue
try:
resp = requests.get(
f"https://topgservers.net/api/v1/vote-check?username={name}",
headers={"Authorization": f"Bearer {API_KEY}"},
timeout=5
)
if resp.status_code == 200 and resp.json().get("voted"):
votes[name] = {"voted": True, "rewarded": False}
except Exception:
continue
with open(VOTES_FILE, 'w') as f:
json.dump(votes, f, indent=2)
if __name__ == "__main__":
print("topgservers vote checker running...")
while True:
check_votes()
time.sleep(CHECK_INTERVAL) 3 Create the Enforce Script mod
The Enforce Script mod reads the votes.json file on a timer and spawns reward items into the player's inventory.
// TopGVote Reward Mod for DayZ
// Reads votes.json written by the Python sidecar
// and grants items to players who voted.
class TopGVoteReward extends PluginBase
{
private const float CHECK_INTERVAL = 30.0; // seconds
private const string VOTES_FILE = "$profile:votes.json";
void TopGVoteReward()
{
GetGame().GetCallQueue(CALL_CATEGORY_SYSTEM)
.CallLater(CheckVotes, CHECK_INTERVAL * 1000, true);
}
void CheckVotes()
{
if (!FileExist(VOTES_FILE)) return;
string content;
FileHandle file = OpenFile(VOTES_FILE, FileMode.READ);
if (!file) return;
string line;
while (FGets(file, line) >= 0)
{
content += line;
}
CloseFile(file);
// Parse JSON and check each online player
array<Man> players = new array<Man>();
GetGame().GetPlayers(players);
foreach (Man man : players)
{
PlayerBase player = PlayerBase.Cast(man);
if (!player) continue;
string name = player.GetIdentity().GetName();
// Simple check: look for the player name with voted:true
if (content.Contains(name)
&& content.Contains(""voted": true")
&& !content.Contains(""rewarded": true"))
{
GrantReward(player);
MarkRewarded(name);
}
}
}
void GrantReward(PlayerBase player)
{
EntityAI item;
// Spawn items in player inventory
item = player.GetInventory().CreateInInventory("SodaCan_Cola");
item = player.GetInventory().CreateInInventory("TacticalBaconCan");
item = player.GetInventory().CreateInInventory("Ammo_762x39");
// Notify player
if (player.GetIdentity())
{
GetGame().RPCSingleParam(player, ERPCs.RPC_USER_ACTION_MESSAGE,
new Param1<string>(
"Thanks for voting on topgservers! Check your inventory."),
true, player.GetIdentity());
}
}
void MarkRewarded(string playerName)
{
// Write back to votes.json marking player as rewarded
// In production, use proper JSON parsing
// For simplicity, the Python sidecar handles cleanup
}
} 4 Create the mod config
The config.cpp registers the mod with DayZ so it loads automatically.
class CfgPatches
{
class TopGVote
{
units[] = {};
weapons[] = {};
requiredVersion = 0.1;
requiredAddons[] = { "DZ_Data" };
};
};
class CfgMods
{
class TopGVote
{
type = "mod";
name = "TopGVote";
dir = "TopGVote";
class defs
{
class worldScriptModule
{
value = "";
files[] = { "TopGVote/Scripts/4_World" };
};
};
};
}; Configuration
# Configuration
API_KEY = "tgs_your_api_key_here"
WEBHOOK_SECRET = "whsec_your_secret_here"
# Paths
VOTES_FILE = "votes.json"
PLAYERS_FILE = "online_players.txt"
# Timing
CHECK_INTERVAL = 60 # seconds between vote checks
# Reward items (DayZ class names)
REWARD_ITEMS = [
"SodaCan_Cola",
"TacticalBaconCan",
"Ammo_762x39",
] Vote Check
Call the /api/v1/vote-check endpoint to determine if a player has voted today.
import requests
resp = requests.get(
"https://topgservers.net/api/v1/vote-check?username=" + player_name,
headers={"Authorization": "Bearer " + API_KEY},
timeout=5
)
if resp.status_code == 200 and resp.json().get("voted"):
# Player voted today — write to votes.json for the mod to read
votes[player_name] = {"voted": True, "rewarded": False} Webhook Receiver
Verify the X-TopG-Signature header using HMAC-SHA256 to ensure webhook payloads are authentic.
"""
Webhook receiver for DayZ servers.
Writes vote results to votes.json for the Enforce Script mod.
"""
import hmac, hashlib, json
from http.server import HTTPServer, BaseHTTPRequestHandler
WEBHOOK_SECRET = "whsec_your_secret_here"
VOTES_FILE = "votes.json"
class WebhookHandler(BaseHTTPRequestHandler):
def do_POST(self):
length = int(self.headers.get('Content-Length', 0))
body = self.rfile.read(length).decode()
sig = self.headers.get('X-TopG-Signature', '')
if not verify_signature(body, sig):
self.send_response(401)
self.end_headers()
return
data = json.loads(body)
username = data.get('username', '')
if username:
# Load existing votes
try:
with open(VOTES_FILE, 'r') as f:
votes = json.load(f)
except (FileNotFoundError, json.JSONDecodeError):
votes = {}
votes[username] = {"voted": True, "rewarded": False}
with open(VOTES_FILE, 'w') as f:
json.dump(votes, f, indent=2)
self.send_response(200)
self.end_headers()
def verify_signature(body, sig_header):
parts = dict(p.split('=', 1) for p in sig_header.split(',') if '=' in p)
timestamp = parts.get('t', '')
received = parts.get('v1', '')
expected = hmac.new(
WEBHOOK_SECRET.encode(),
f"{timestamp}.{body}".encode(),
hashlib.sha256
).hexdigest()
return hmac.compare_digest(expected, received)
if __name__ == '__main__':
server = HTTPServer(('0.0.0.0', 8090), WebhookHandler)
print("Webhook receiver listening on :8090")
server.serve_forever() Reward Examples
// Spawn item in player inventory
player.GetInventory().CreateInInventory("SodaCan_Cola");
player.GetInventory().CreateInInventory("TacticalBaconCan");
// Spawn ammo
player.GetInventory().CreateInInventory("Ammo_762x39");
// Spawn weapon (goes to hands if space)
player.GetInventory().CreateInInventory("M4A1");
// Spawn item at player position (if inventory is full)
EntityAI item = GetGame().CreateObjectEx(
"TacticalBaconCan", player.GetPosition(),
ECE_PLACE_ON_SURFACE);
// Send notification
GetGame().RPCSingleParam(player, ERPCs.RPC_USER_ACTION_MESSAGE,
new Param1<string>("Vote reward: items added!"),
true, player.GetIdentity()); Notes & Tips
DayZ Enforce Script cannot make HTTP requests directly, so the Python sidecar pattern is required. The sidecar writes to votes.json and the mod reads it. For production, consider using a SQLite database instead of a JSON file for better concurrency. Make sure the votes.json path is accessible to both the Python script and the DayZ server process.