ServerAnalytics configuration
The ServerAnalytics config.json controls how the plugin runs on your Ark Survival Ascended server. Every setting is listed below with what it does and its default value.
Where it lives
Drop the file on your server at ArkApi/Plugins/ServerAnalytics/config.json then reload the plugin or restart the server. Keep a backup before large changes.
Every setting
Language
Which language file to use from the lang folder. "en" reads lang/en.json. Make a copy like lang/de.json, translate the lines, and put "de" here. If a line is missing from your file, the built in English line is used, so nothing ever shows blank.
LangAutoFill
When true, I add any new text lines to your language file after an update. I never touch lines you already wrote, and I save the old file next to it as a .bak first. Set false if you want your language files left alone completely.
SenderName
The name shown in chat when I speak, instead of the plain (SERVER) tag. Leave "" to keep the normal server tag. Example: "The Bookkeeper". You can use {map} and {server} inside it, like "Books of {map}". This only changes chat lines. The on screen popups are not touched by it.
General
- Debug togglefalse
- When true, I write extra detail to ArkApi.log so problems are easy to chase. Leave false for a quiet log on a healthy server. Turn on when NordBots support asks.
Server
How I learn which server my books belong to. One config.json can go out to every map in your cluster and each copy still signs its own name, because I read the name straight from the way you start the server. You will most likely never need to touch this block at all.
- Name textempty
- Name: a name written here beats everything else. It is used exactly as typed. Keep it "" and I find the name on my own, which is the setup that lets one config file serve nine maps.
- NameFromParams list["-ServerName=","-serverkey=","-clustermap=","?SessionName="]
- NameFromParams: the start line switches I check, first hit wins. Most launchers already pass one of these four. Runs ArkShop too? Then -serverkey= is already on your line and I pick it up with no work from you. Add another entry if your panel writes the name behind a different switch.
- UseSessionName togglefalse
- UseSessionName: true lets me also try the session name the game shows in the server browser, after the start line gave me nothing. Off by default, since many hosts stuff that field with rates and ads.
- Id textempty
- Id: a short lowercase tag squeezed out of the name, for places that want a handle instead of a title. Leave "" and I make one from the name I found. Only set it yourself if two servers boil down to the same tag.
License
- Key textempty
- Your ServerAnalytics license key from NordBots.cc. It looks like NB-XXXX-XXXX. With no key here I still load, but I record nothing until one is set. After pasting the key, run ServerAnalytics.Reload from the console and watch the log.
Cluster
- ClusterName textempty
- A short name for your whole cluster, the same on every server in it. Example: "arkstar-monthly". With "" I use the word cluster. Every saved row carries this name, so one database can hold many clusters apart.
- ServerName textempty
- A short name for THIS server, different on every map in the cluster. Example: "island-1". With "" I use the name the Server block above worked out from your launch line, which is usually exactly what you want. Two servers must never share this name, or their rows blend together.
- Season textempty
- The name of the current wipe or season, like "wipe-2026-08". Change it when you wipe and I start a fresh season page. Old rows keep the old name. With "" I call the season open and just keep counting.
Database
- Mode text"sqlite"
- Where I keep my books. "sqlite" needs zero setup and lives in my data folder. "mysql" lets every server in the cluster write into one shared database. Pick "mysql" when you run more than one map or want a website to read the data.
- TablePrefix text"sa"
- The first part of every table name, like sa_players and sa_sessions. Leave it as "sa" unless another tool in your database already uses those names. Websites and bots read these names, so change it once at the start or never.
- MakeViews toggletrue
- When true and you are on MySQL, I build three read only views your website or bot can read without knowing my table shapes: player totals, player combat, tribe time. Set false if your MySQL user is not allowed to create views. SQLite skips this.
- MySQL group
- Host textempty
- The address of your MySQL server. Example: "127.0.0.1".
- Port number3306
- The port of your MySQL server. Almost always 3306.
- User textempty
- The MySQL user I log in as. Give it rights on the database below.
- Password textempty
- That user's password.
- Database textempty
- The database name my tables live in. Example: "arkstats".
Track
- Sessions toggletrue
- Record sessions and playtime. Who joined, when they left, how long they played, and how much of that time they stood still. This is the heart of the plugin.
- Tribes toggletrue
- Record tribe life. Joins, leaves, kicks, merges, and renames, with the time of each.
- Combat toggletrue
- Record player deaths. Who fell, who did it, player or creature or the world, same tribe or not, and where it happened. Also totals up player damage in short windows, so a raid becomes a handful of rows instead of a million.
- Dinos toggletrue
- Record dino life. Tames with the level, wild and boss kills by players, and tamed dinos lost, with the species and the tribe.
- AdminActions toggletrue
- Record admin life. Every tracked admin command, creative mode going on and off, and every command that comes in over RCON. This is the audit page.
- Crafting toggletrue
- Record who asked to craft what, and whether it was their own bag or a station. A station craft with no clear person is filed to the tribe, never guessed onto a player.
- Structures toggletrue
- Record building and raids. Structures placed and destroyed, plus a raid timeline that opens when one tribe starts hitting another and closes after things go quiet.
- ResourceGains togglefalse
- Record resources landing in player bags. This one is still being proven, so it ships off. Turn it on only if you are helping test it, and treat the numbers as a rough guide until we say otherwise. Nothing else is affected either way.
Keep
- CombatDays number180
- How many days of death rows to keep. 0 means keep them forever. 180 gives you half a year of history. A smaller number keeps the database lean. Every night I quietly sweep out rows older than this.
- SessionsDays number0
- How many days of finished sessions to keep. 0 means forever. Playtime totals come from these rows, so trimming them trims old totals too.
- TribeEventsDays number0
- How many days of tribe events to keep. 0 means forever. These rows are small, so forever costs almost nothing.
- DamageWindowDays number14
- How many days of damage window rows to keep. These are the busiest rows I write, so they get the shortest life. Two weeks covers most raid arguments.
- DinoEventsDays number0
- How many days of dino rows to keep. 0 means forever.
- AdminDays number0
- How many days of admin audit rows to keep. 0 means forever, and I suggest leaving it there. The audit is worth the space.
- StructureDays number60
- How many days of building and raid rows to keep. 0 means forever.
- GainsWindowDays number30
- How many days of resource gain and craft rows to keep. 0 means forever.
- WatchDays number30
- How many days of close watch rows to keep. 0 means forever. These are the most detailed rows I write, so a shorter life is kinder to your disk.
- ChatDays number30
- How many days of chat lines to keep in the <prefix>_chat table. 0 keeps them forever. Chat is the biggest table on a busy server, so 30 is a sensible floor and 90 is plenty for a moderation trail.
Alerts
- CreativeUse toggletrue
- When true I send a Discord alert the moment creative mode comes on for anyone.
- AdminGives toggletrue
- When true I send a Discord alert when an admin command from my watch list runs, like giveitem or spawndino. The list itself lives under Advanced. I look past a leading "cheat" or "admincheat", so a tool that sends "admincheat GFI ..." still trips the alert for gfi.
- RconCommands text"watchlist"
- RconCommands: how much RCON traffic reaches your Discord webhook. Every command is always written to the audit no matter what; this only picks the Discord posts. "watchlist" sends only commands from the watch list above. This is the default. "all" sends every RCON command as a quiet post, and watch list hits still go to the alert route. The PostsPerMinute cap in discord.json holds the flood back if a bot gets chatty. "off" sends nothing from RCON to Discord at all.
- MutedHours textempty
- A quiet window when alerts stay silent, for planned maintenance. Write it as start-end in 24 hour time, like "02:00-04:00". Leave "" for no quiet time. Everything is still written to the audit, only the Discord ping is held.
Wire
------------------------------------------------------------------ Wire: talk to Discord both ways, through the NordBots bot. This is the one that puts your in game chat in a Discord channel, and puts anything typed in that channel back into your game. You do not host anything and you do not make your own Discord bot. You invite ours. How to turn it on, start to finish: 1. Set Enabled below to true and put your NB- key under License. 2. Start the server. Look in ArkApi.log for the line that gives you your server key. 3. In your own Discord, invite the NordBots bot, then run /link and paste that server key. 4. Run /channel lane:chat channel:#wherever-you-want-chat One thing to think about before step 4. Anyone who can type in that channel can talk to your game server. Set the channel up the way you want it first. Your players' chat goes straight from this server to your own Discord. It never passes through us. Only the other direction does. ------------------------------------------------------------------
- Enabled togglefalse
- Master switch. Off by default. Nothing reaches the internet for this until you turn it on.
- Relay text"https://api.nordbots.cc/wire/v1"
- Where the NordBots wire lives. Leave this alone unless we tell you to change it.
- Out toggletrue
- Out: send your game chat to Discord. In: let lines typed in Discord show up in game. Turn either one off on its own. Off and off is the same as Enabled false.
- In toggletrue
- Global toggletrue
- Which kinds of chat get sent out. Global is the normal one everybody reads, so it is on. Tribe and Alliance are private talk between players. Putting those in a Discord channel is a real betrayal of the people typing them, so both ship off. Turn them on only if your players know and agree. Local is proximity chat, which is noisy and rarely worth it.
- Tribe togglefalse
- Alliance togglefalse
- Local togglefalse
- HideCommands toggletrue
- true means a line that was a plugin command, like /mystats, is not sent to Discord. Leave it true. Nobody needs to read your players' commands, and it quietly shows how your staff work.
- StoreChat toggletrue
- Write every chat line to your database, in the <prefix>_chat table. This works even with Enabled false, and it is worth having on its own. The day you are handed a harassment report, this is the only place that remembers what was actually said. Trimmed by Keep.ChatDays.
- Prefix text"[Discord]"
- The little tag in front of a line that came from Discord, so players can tell it apart from someone in game. Set it to "" for no tag.
- LineFormat text"{message}"
- The line that lands in Discord. Discord markdown works here, so **bold** and `code` do what you expect. Some to try: "{message}" just the words, tidiest "{t} `{map}` **{player}**: {message}" time, map, name "**[{mode}]** {player}: {message}" handy if tribe chat is on "{R} {player} ({tribe}): {message}" shows how long ago
- NameFormat text"{player}"
- The name Discord shows as the author of the line. Leave it as {player} and each message looks like it came from that person. Set it to {map} or {server} and every line comes from the server instead, which reads better when your LineFormat already names the player. Empty means the webhook's own name is used.
- InGameFormat text"{prefix} {player}: {message}"
- The line that lands in game when somebody types in Discord. Keep it short. Chat boxes are small. "{prefix} {player}: {message}" the normal one "{clock} {prefix} {player}: {message}" with a plain clock
- TimeStyle text"t"
- Which clock {time} uses. One letter: t T d D f F R. See the list above.
- EscapeMarkdown toggletrue
- true stops a player breaking your Discord channel by typing markdown. Someone writing **hi** shows up as **hi** and not as bold. Turn it off only if you trust everyone on your server.
- AvatarURL textempty
- A picture to show next to each line in Discord. You can use the same pieces here, so a service that serves images by EOS id would look like "https://example.com/faces/{eos}.png". Leave empty for no picture.
- Colour text"Cyan"
- The colour of those lines in chat. One of: White, Green, Red, Yellow, Orange, Blue, Purple, Pink, Grey, Cyan.
- MaxLength number220
- Longest Discord line I will put in game, in characters. Anything longer is cut on a word and gets a "..." on the end. Bigger means long Discord posts fill the chat box. 220 reads well. Under 40 is ignored.
- KeepLinks togglefalse
- false turns a web link into just its site name, so a huge tracking link reads as "example.com link". true prints the whole thing, which is ugly in game and is a way for someone to push a link at your players.
- MinBackoffSeconds number5
- If the wire goes quiet I wait, then wait longer each try, so a hiccup on our side does not turn into a flood of retries from every server at once. MinBackoffSeconds is the first wait, MaxBackoffSeconds is the longest I will ever wait. Chat going out to Discord keeps working the whole time.
- MaxBackoffSeconds number300
- MaxInboundPerMinute number30
- Most Discord lines I will put in game in one minute. Anything past this is dropped. It stops one person spamming your Discord channel from burying your in game chat. Raise it on a quiet server, lower it on a busy one.
- SeenJobs number200
- How many recent jobs I remember so a repeat never runs twice. You should never need to change this.
Commands
- MyStats text"/mystats"
- The chat command a player types to see their own record. Rename it if another plugin already uses /mystats. Set "" to turn it off.
- TribeStats text"/tribestats"
- The chat command for the tribe page. Set "" to turn it off.
- Top text"/top"
- The leaderboard command. A player can add a board name after it: /top time, /top kills, or /top tames. Plain /top shows time. Set "" to turn it off.
Advanced
- HeartbeatSeconds number60
- How often each online player's session row is refreshed in the database, in seconds. If the server dies, a player can lose at most this many seconds of playtime. Smaller writes more often. Bigger writes less and risks a little more on a crash.
- AfkAfterSeconds number300
- How many seconds a player must stand still before I count their time as idle.
- IdleMoveThreshold number50
- How far a player must move, in game units, for me to call it moving. 50 is about half a footstep. Raise it if turrets or elevators fool it.
- MaxQueuedWrites number20000
- The most database moves I hold in memory when the database is slow. Above this I shed only the cheap refresh writes and count what I shed in Status. Real events are never shed. They go to my spool file instead.
- SpoolReplayMinutes number5
- How often I check my spool file and write saved rows back once the database returns, in minutes.
- MaintenanceHour number5
- The hour of the server clock when I do my nightly sweep of old rows. 5 means 5 in the morning.
- DamageWindowSeconds number10
- How many seconds of player damage get rolled into one row. 10 keeps raid detail sharp. A bigger number writes fewer, coarser rows.
- GainsWindowSeconds number60
- How many seconds of resource pickups get rolled into one row per player per item. 60 is a good balance. Only matters when Track then ResourceGains is on.
- GainsStudyRows number0
- For testing only. Above 0, I also save that many raw resource pickup rows so we can study how the game reports them. Leave at 0 on a live server.
- RaidQuietMinutes number10
- How many quiet minutes end a raid timeline. If nobody hits the base again within this many minutes, I close the raid and write it up.
- RaidMinHits number25
- How many hits a raid needs before I post it to Discord. Small scuffles are still written to the database, they just do not ping your channel.
- MaxWatched number5
- The most players I will watch closely at one time. Each watch writes a lot of rows, so this keeps a busy night from filling your disk.
- AlertCommands list["giveitem","gfi","giveitemtoplayer","summon","gmsummon","spawndino","destroyall","destroyallenemies","god","infinitestats","givetome"]
- The admin commands that fire a Discord alert. I match the first word only, with or without a leading slash, and case does not matter.
- BossClassContains list["Boss","Overseer","Rockwell","Dinopithecus_King","Manticore","Dragon_Character"]
- Words that mark a creature class as a boss. I check each dino's name tag and species once per class and remember the answer, so this costs nothing in play.
Panel
- Enabled toggletrue
- The stats window players can click through, drawn by the free NordBots UI mod. True means I look for the mod and open the window next to my chat replies. False means I never look for the mod at all and everything stays chat only.
- RowsPerPage number10
- How many rows fit on one page of a plain list window. Every plugin with a window shares this same block, so the setting rides along here too. My own pages are short fixed lists and the leaderboard follows TopCount below, so this one changes nothing for me today. 12 is the most the wire can carry.
- TopCount number10
- How many names one page of the Top players window shows. It has its own number so you can keep other pages short and still show a full top ten. Also capped at 12.
- BuffTag text"NordBotsUIBuff"
- The tag I search for on the mod's buff. The buff is my road to a player's screen. Only change this if a mod update tells you the tag changed.
- BuffPath text"NordBotsUI/Buff_NordBotsUI"
- The folder the mod's buff lives in. When the tag is missing I match on this instead, so an untagged buff still works. Leave it as it ships.
- SingletonPath text"Blueprint'/NordBotsUI/NordBotsUI_Singleton.NordBotsUI_Singleton'"
- The mod actor I read the protocol version from before I send anything. Leave it as it ships unless the mod maker says it moved.
- RequireHandshake togglefalse
- My choice when the mod carries no version number at all. False means I send the window anyway and trust the mod to skip anything it does not understand. That is the right call for almost every server. True means I hold every window back until I can read a version that matches mine. A version that truly disagrees with mine always stays off, no matter what this says.
ApiUtilsMod
- Enabled toggletrue
- When true and the free ASA API Utils mod is on the server, my messages show as clean on screen panels instead of plain chat. Without the mod I just talk in chat as normal.
- BackdropColor list[0,0,0,0.55]
- The panel background color as red, green, blue, alpha from 0.0 to 1.0. The last number is see through. 0.55 is a soft dark glass.
- ScreenPosition text"Center"
- Where the panel sits on screen: "Left", "Center", or "Right".
- TextAlign text"Center"
- How the text lines up inside the panel: "Left", "Center", or "Right".
- TextScale number1
- How big the text is. 1.0 is normal. 1.5 is half again as big.
- MessageSeconds number6
- How many seconds the panel stays on screen.
- AlsoShowInChat toggletrue
- When true the same words also land in the chat log, so nobody misses them. That means two messages per send when the mod is on.
MapName
- Pretty toggletrue
- When true I turn map file names like TheIsland_WP into The Island everywhere I speak.
- Overrides group
- Set your own names for maps here. The left side is the raw file name. Example: { "TheIsland_WP": "Home Island" }
The full commented config
This is a reading copy with notes. It is not valid JSON, so do not load it. Use the editor or the plain config.json instead.
// ServerAnalytics settings, explained line by line.
// This file is only a guide. The server reads config.json, not this file.
// Copy the parts you change into config.json and keep that file as plain JSON with no comments.
{
// Which language file to use from the lang folder.
// "en" reads lang/en.json. Make a copy like lang/de.json, translate the lines, and put "de" here.
// If a line is missing from your file, the built in English line is used, so nothing ever shows blank.
"Language": "en",
// When true, I add any new text lines to your language file after an update.
// I never touch lines you already wrote, and I save the old file next to it as a .bak first.
// Set false if you want your language files left alone completely.
"LangAutoFill": true,
// The name shown in chat when I speak, instead of the plain (SERVER) tag.
// Leave "" to keep the normal server tag. Example: "The Bookkeeper".
// You can use {map} and {server} inside it, like "Books of {map}".
// This only changes chat lines. The on screen popups are not touched by it.
"SenderName": "",
"General": {
// When true, I write extra detail to ArkApi.log so problems are easy to chase.
// Leave false for a quiet log on a healthy server. Turn on when NordBots support asks.
"Debug": false
},
// How I learn which server my books belong to. One config.json can go out to every
// map in your cluster and each copy still signs its own name, because I read the
// name straight from the way you start the server. You will most likely never need
// to touch this block at all.
"Server": {
// Name: a name written here beats everything else. It is used exactly as typed.
// Keep it "" and I find the name on my own, which is the setup that lets one
// config file serve nine maps.
"Name": "",
// NameFromParams: the start line switches I check, first hit wins. Most launchers
// already pass one of these four. Runs ArkShop too? Then -serverkey= is already
// on your line and I pick it up with no work from you. Add another entry if your
// panel writes the name behind a different switch.
"NameFromParams": [
"-ServerName=",
"-serverkey=",
"-clustermap=",
"?SessionName="
],
// UseSessionName: true lets me also try the session name the game shows in the
// server browser, after the start line gave me nothing. Off by default, since
// many hosts stuff that field with rates and ads.
"UseSessionName": false,
// Id: a short lowercase tag squeezed out of the name, for places that want a
// handle instead of a title. Leave "" and I make one from the name I found.
// Only set it yourself if two servers boil down to the same tag.
"Id": ""
},
"License": {
// Your ServerAnalytics license key from NordBots.cc. It looks like NB-XXXX-XXXX.
// With no key here I still load, but I record nothing until one is set.
// After pasting the key, run ServerAnalytics.Reload from the console and watch the log.
"Key": ""
},
"Cluster": {
// A short name for your whole cluster, the same on every server in it.
// Example: "arkstar-monthly". With "" I use the word cluster.
// Every saved row carries this name, so one database can hold many clusters apart.
"ClusterName": "",
// A short name for THIS server, different on every map in the cluster.
// Example: "island-1". With "" I use the name the Server block above worked out
// from your launch line, which is usually exactly what you want.
// Two servers must never share this name, or their rows blend together.
"ServerName": "",
// The name of the current wipe or season, like "wipe-2026-08".
// Change it when you wipe and I start a fresh season page. Old rows keep the old name.
// With "" I call the season open and just keep counting.
"Season": ""
},
"Database": {
// Where I keep my books. "sqlite" needs zero setup and lives in my data folder.
// "mysql" lets every server in the cluster write into one shared database.
// Pick "mysql" when you run more than one map or want a website to read the data.
"Mode": "sqlite",
// The first part of every table name, like sa_players and sa_sessions.
// Leave it as "sa" unless another tool in your database already uses those names.
// Websites and bots read these names, so change it once at the start or never.
"TablePrefix": "sa",
// When true and you are on MySQL, I build three read only views your website or bot
// can read without knowing my table shapes: player totals, player combat, tribe time.
// Set false if your MySQL user is not allowed to create views. SQLite skips this.
"MakeViews": true,
"MySQL": {
// The address of your MySQL server. Example: "127.0.0.1".
"Host": "",
// The port of your MySQL server. Almost always 3306.
"Port": 3306,
// The MySQL user I log in as. Give it rights on the database below.
"User": "",
// That user's password.
"Password": "",
// The database name my tables live in. Example: "arkstats".
"Database": ""
}
},
"Track": {
// Record sessions and playtime. Who joined, when they left, how long they played,
// and how much of that time they stood still. This is the heart of the plugin.
"Sessions": true,
// Record tribe life. Joins, leaves, kicks, merges, and renames, with the time of each.
"Tribes": true,
// Record player deaths. Who fell, who did it, player or creature or the world,
// same tribe or not, and where it happened. Also totals up player damage in
// short windows, so a raid becomes a handful of rows instead of a million.
"Combat": true,
// Record dino life. Tames with the level, wild and boss kills by players,
// and tamed dinos lost, with the species and the tribe.
"Dinos": true,
// Record admin life. Every tracked admin command, creative mode going on and off,
// and every command that comes in over RCON. This is the audit page.
"AdminActions": true,
// Record who asked to craft what, and whether it was their own bag or a station.
// A station craft with no clear person is filed to the tribe, never guessed onto a player.
"Crafting": true,
// Record building and raids. Structures placed and destroyed, plus a raid timeline
// that opens when one tribe starts hitting another and closes after things go quiet.
"Structures": true,
// Record resources landing in player bags. This one is still being proven, so it
// ships off. Turn it on only if you are helping test it, and treat the numbers as
// a rough guide until we say otherwise. Nothing else is affected either way.
"ResourceGains": false
},
"Keep": {
// How many days of death rows to keep. 0 means keep them forever.
// 180 gives you half a year of history. A smaller number keeps the database lean.
// Every night I quietly sweep out rows older than this.
"CombatDays": 180,
// How many days of finished sessions to keep. 0 means forever.
// Playtime totals come from these rows, so trimming them trims old totals too.
"SessionsDays": 0,
// How many days of tribe events to keep. 0 means forever.
// These rows are small, so forever costs almost nothing.
"TribeEventsDays": 0,
// How many days of damage window rows to keep. These are the busiest rows I write,
// so they get the shortest life. Two weeks covers most raid arguments.
"DamageWindowDays": 14,
// How many days of dino rows to keep. 0 means forever.
"DinoEventsDays": 0,
// How many days of admin audit rows to keep. 0 means forever, and I suggest
// leaving it there. The audit is worth the space.
"AdminDays": 0,
// How many days of building and raid rows to keep. 0 means forever.
"StructureDays": 60,
// How many days of resource gain and craft rows to keep. 0 means forever.
"GainsWindowDays": 30,
// How many days of close watch rows to keep. 0 means forever.
// These are the most detailed rows I write, so a shorter life is kinder to your disk.
"WatchDays": 30,
// How many days of chat lines to keep in the <prefix>_chat table.
// 0 keeps them forever. Chat is the biggest table on a busy server, so
// 30 is a sensible floor and 90 is plenty for a moderation trail.
"ChatDays": 30
},
"Alerts": {
// When true I send a Discord alert the moment creative mode comes on for anyone.
"CreativeUse": true,
// When true I send a Discord alert when an admin command from my watch list runs,
// like giveitem or spawndino. The list itself lives under Advanced. I look past a
// leading "cheat" or "admincheat", so a tool that sends "admincheat GFI ..." still
// trips the alert for gfi.
"AdminGives": true,
// RconCommands: how much RCON traffic reaches your Discord webhook. Every command
// is always written to the audit no matter what; this only picks the Discord posts.
// "watchlist" sends only commands from the watch list above. This is the default.
// "all" sends every RCON command as a quiet post, and watch list hits still go
// to the alert route. The PostsPerMinute cap in discord.json holds the
// flood back if a bot gets chatty.
// "off" sends nothing from RCON to Discord at all.
"RconCommands": "watchlist",
// A quiet window when alerts stay silent, for planned maintenance.
// Write it as start-end in 24 hour time, like "02:00-04:00". Leave "" for no quiet time.
// Everything is still written to the audit, only the Discord ping is held.
"MutedHours": ""
},
// ------------------------------------------------------------------
// Wire: talk to Discord both ways, through the NordBots bot.
//
// This is the one that puts your in game chat in a Discord channel, and
// puts anything typed in that channel back into your game. You do not host
// anything and you do not make your own Discord bot. You invite ours.
//
// How to turn it on, start to finish:
// 1. Set Enabled below to true and put your NB- key under License.
// 2. Start the server. Look in ArkApi.log for the line that gives you
// your server key.
// 3. In your own Discord, invite the NordBots bot, then run
// /link and paste that server key.
// 4. Run /channel lane:chat channel:#wherever-you-want-chat
//
// One thing to think about before step 4. Anyone who can type in that
// channel can talk to your game server. Set the channel up the way you
// want it first.
//
// Your players' chat goes straight from this server to your own Discord.
// It never passes through us. Only the other direction does.
// ------------------------------------------------------------------
"Wire": {
// Master switch. Off by default. Nothing reaches the internet for this
// until you turn it on.
"Enabled": false,
// Where the NordBots wire lives. Leave this alone unless we tell you to
// change it.
"Relay": "https://api.nordbots.cc/wire/v1",
// Out: send your game chat to Discord.
// In: let lines typed in Discord show up in game.
// Turn either one off on its own. Off and off is the same as Enabled false.
"Out": true,
"In": true,
// Which kinds of chat get sent out.
//
// Global is the normal one everybody reads, so it is on.
// Tribe and Alliance are private talk between players. Putting those in a
// Discord channel is a real betrayal of the people typing them, so both
// ship off. Turn them on only if your players know and agree.
// Local is proximity chat, which is noisy and rarely worth it.
"Global": true,
"Tribe": false,
"Alliance": false,
"Local": false,
// true means a line that was a plugin command, like /mystats, is not sent
// to Discord. Leave it true. Nobody needs to read your players' commands,
// and it quietly shows how your staff work.
"HideCommands": true,
// Write every chat line to your database, in the <prefix>_chat table.
// This works even with Enabled false, and it is worth having on its own.
// The day you are handed a harassment report, this is the only place that
// remembers what was actually said. Trimmed by Keep.ChatDays.
"StoreChat": true,
// The little tag in front of a line that came from Discord, so players can
// tell it apart from someone in game. Set it to "" for no tag.
"Prefix": "[Discord]",
// ----------------------------------------------------------------
// How a chat line is written, both ways.
//
// You build the line yourself out of the pieces below. Put a piece in
// curly brackets and I swap it for the real thing. Anything I do not
// know I leave alone, so a stray {word} shows up as you typed it.
//
// WHO CAN SAY IT
// {player} {name} the survivor name
// {eos} their EOS id, the long number that never changes
// {tribe} their tribe, or "no tribe"
// {team} the tribe number
// {mode} Global, Tribe, Alliance or Local
//
// WHERE THEY SAID IT
// {map} the tidy map name, like The Island
// {server} what this server calls itself
// {tag} the short name, like the-island
// {cluster} your cluster name
// {season} your season tag
// {online} how many people are on right now
//
// WHAT THEY SAID
// {message} {text} the words
// {prefix} the Prefix setting above, in game only
// {origin} which map a line came from, cluster chat only
//
// WHEN THEY SAID IT
// Discord draws these live, in each reader's own time zone, so a player
// in Sydney and one in Texas both see their own clock. Pick the shape:
// {t} 16:20 short time
// {T} 16:20:30 long time
// {d} 20/04/2026 short date
// {D} 20 April 2026 long date
// {f} 20 April 2026 16:20 date and time
// {F} Monday, 20 April 2026 16:20 the lot
// {R} 2 minutes ago counts up on its own
// {time} whichever one TimeStyle picks below
// {unix} the raw number, if you want to build your own
// In game those same names give plain text instead, because the game
// cannot draw Discord's live clocks. {clock} {clock12} {date} also work
// in both places.
// ----------------------------------------------------------------
// The line that lands in Discord. Discord markdown works here, so **bold**
// and `code` do what you expect.
//
// Some to try:
// "{message}" just the words, tidiest
// "{t} `{map}` **{player}**: {message}" time, map, name
// "**[{mode}]** {player}: {message}" handy if tribe chat is on
// "{R} {player} ({tribe}): {message}" shows how long ago
"LineFormat": "{message}",
// The name Discord shows as the author of the line. Leave it as {player}
// and each message looks like it came from that person. Set it to {map}
// or {server} and every line comes from the server instead, which reads
// better when your LineFormat already names the player.
// Empty means the webhook's own name is used.
"NameFormat": "{player}",
// The line that lands in game when somebody types in Discord.
// Keep it short. Chat boxes are small.
// "{prefix} {player}: {message}" the normal one
// "{clock} {prefix} {player}: {message}" with a plain clock
"InGameFormat": "{prefix} {player}: {message}",
// Which clock {time} uses. One letter: t T d D f F R. See the list above.
"TimeStyle": "t",
// true stops a player breaking your Discord channel by typing markdown.
// Someone writing **hi** shows up as **hi** and not as bold. Turn it off
// only if you trust everyone on your server.
"EscapeMarkdown": true,
// A picture to show next to each line in Discord. You can use the same
// pieces here, so a service that serves images by EOS id would look like
// "https://example.com/faces/{eos}.png". Leave empty for no picture.
"AvatarURL": "",
// The colour of those lines in chat. One of:
// White, Green, Red, Yellow, Orange, Blue, Purple, Pink, Grey, Cyan.
"Colour": "Cyan",
// Longest Discord line I will put in game, in characters. Anything longer
// is cut on a word and gets a "..." on the end. Bigger means long Discord
// posts fill the chat box. 220 reads well. Under 40 is ignored.
"MaxLength": 220,
// false turns a web link into just its site name, so a huge tracking link
// reads as "example.com link". true prints the whole thing, which is ugly
// in game and is a way for someone to push a link at your players.
"KeepLinks": false,
// If the wire goes quiet I wait, then wait longer each try, so a hiccup on
// our side does not turn into a flood of retries from every server at once.
// MinBackoffSeconds is the first wait, MaxBackoffSeconds is the longest I
// will ever wait. Chat going out to Discord keeps working the whole time.
"MinBackoffSeconds": 5,
"MaxBackoffSeconds": 300,
// Most Discord lines I will put in game in one minute. Anything past this
// is dropped. It stops one person spamming your Discord channel from
// burying your in game chat. Raise it on a quiet server, lower it on a
// busy one.
"MaxInboundPerMinute": 30,
// How many recent jobs I remember so a repeat never runs twice. You should
// never need to change this.
"SeenJobs": 200
},
"Commands": {
// The chat command a player types to see their own record.
// Rename it if another plugin already uses /mystats. Set "" to turn it off.
"MyStats": "/mystats",
// The chat command for the tribe page. Set "" to turn it off.
"TribeStats": "/tribestats",
// The leaderboard command. A player can add a board name after it:
// /top time, /top kills, or /top tames. Plain /top shows time. Set "" to turn it off.
"Top": "/top"
},
// Discord: the webhook settings have their own home now, discord.json, beside this
// config. Edit them there. Keys are the same ones you know: Enabled, WebhookURL, AlertWebhookURL, Username, ServerName, PostsPerMinute.
// If the file is gone I make a new one at boot, and a leftover Discord block in this
// config still works underneath, losing only where discord.json says otherwise.
"Advanced": {
// You probably never need to touch this block. The numbers ship correct.
// How often each online player's session row is refreshed in the database, in seconds.
// If the server dies, a player can lose at most this many seconds of playtime.
// Smaller writes more often. Bigger writes less and risks a little more on a crash.
"HeartbeatSeconds": 60,
// How many seconds a player must stand still before I count their time as idle.
"AfkAfterSeconds": 300,
// How far a player must move, in game units, for me to call it moving.
// 50 is about half a footstep. Raise it if turrets or elevators fool it.
"IdleMoveThreshold": 50.0,
// The most database moves I hold in memory when the database is slow.
// Above this I shed only the cheap refresh writes and count what I shed in Status.
// Real events are never shed. They go to my spool file instead.
"MaxQueuedWrites": 20000,
// How often I check my spool file and write saved rows back once the database returns, in minutes.
"SpoolReplayMinutes": 5,
// The hour of the server clock when I do my nightly sweep of old rows. 5 means 5 in the morning.
"MaintenanceHour": 5,
// How many seconds of player damage get rolled into one row.
// 10 keeps raid detail sharp. A bigger number writes fewer, coarser rows.
"DamageWindowSeconds": 10,
// How many seconds of resource pickups get rolled into one row per player per item.
// 60 is a good balance. Only matters when Track then ResourceGains is on.
"GainsWindowSeconds": 60,
// For testing only. Above 0, I also save that many raw resource pickup rows so we
// can study how the game reports them. Leave at 0 on a live server.
"GainsStudyRows": 0,
// How many quiet minutes end a raid timeline. If nobody hits the base again within
// this many minutes, I close the raid and write it up.
"RaidQuietMinutes": 10,
// How many hits a raid needs before I post it to Discord. Small scuffles are still
// written to the database, they just do not ping your channel.
"RaidMinHits": 25,
// The most players I will watch closely at one time. Each watch writes a lot of rows,
// so this keeps a busy night from filling your disk.
"MaxWatched": 5,
// The admin commands that fire a Discord alert. I match the first word only,
// with or without a leading slash, and case does not matter.
"AlertCommands": ["giveitem", "gfi", "giveitemtoplayer", "summon", "gmsummon", "spawndino", "destroyall", "destroyallenemies", "god", "infinitestats", "givetome"],
// Words that mark a creature class as a boss. I check each dino's name tag and
// species once per class and remember the answer, so this costs nothing in play.
"BossClassContains": ["Boss", "Overseer", "Rockwell", "Dinopithecus_King", "Manticore", "Dragon_Character"]
},
"Panel": {
// The stats window players can click through, drawn by the free NordBots UI mod.
// True means I look for the mod and open the window next to my chat replies.
// False means I never look for the mod at all and everything stays chat only.
"Enabled": true,
// How many rows fit on one page of a plain list window. Every plugin with a
// window shares this same block, so the setting rides along here too. My own
// pages are short fixed lists and the leaderboard follows TopCount below,
// so this one changes nothing for me today. 12 is the most the wire can carry.
"RowsPerPage": 10,
// How many names one page of the Top players window shows. It has its own
// number so you can keep other pages short and still show a full top ten.
// Also capped at 12.
"TopCount": 10,
// The tag I search for on the mod's buff. The buff is my road to a player's
// screen. Only change this if a mod update tells you the tag changed.
"BuffTag": "NordBotsUIBuff",
// The folder the mod's buff lives in. When the tag is missing I match on
// this instead, so an untagged buff still works. Leave it as it ships.
"BuffPath": "NordBotsUI/Buff_NordBotsUI",
// The mod actor I read the protocol version from before I send anything.
// Leave it as it ships unless the mod maker says it moved.
"SingletonPath": "Blueprint'/NordBotsUI/NordBotsUI_Singleton.NordBotsUI_Singleton'",
// My choice when the mod carries no version number at all. False means I send
// the window anyway and trust the mod to skip anything it does not understand.
// That is the right call for almost every server. True means I hold every
// window back until I can read a version that matches mine. A version that
// truly disagrees with mine always stays off, no matter what this says.
"RequireHandshake": false
},
"ApiUtilsMod": {
// When true and the free ASA API Utils mod is on the server, my messages show as clean
// on screen panels instead of plain chat. Without the mod I just talk in chat as normal.
"Enabled": true,
// The panel background color as red, green, blue, alpha from 0.0 to 1.0.
// The last number is see through. 0.55 is a soft dark glass.
"BackdropColor": [0.0, 0.0, 0.0, 0.55],
// Where the panel sits on screen: "Left", "Center", or "Right".
"ScreenPosition": "Center",
// How the text lines up inside the panel: "Left", "Center", or "Right".
"TextAlign": "Center",
// How big the text is. 1.0 is normal. 1.5 is half again as big.
"TextScale": 1.0,
// How many seconds the panel stays on screen.
"MessageSeconds": 6.0,
// When true the same words also land in the chat log, so nobody misses them.
// That means two messages per send when the mod is on.
"AlsoShowInChat": true
},
"MapName": {
// When true I turn map file names like TheIsland_WP into The Island everywhere I speak.
"Pretty": true,
// Set your own names for maps here. The left side is the raw file name.
// Example: { "TheIsland_WP": "Home Island" }
"Overrides": {}
}
}