Skip to content

Server API Reference

The AnalyticsModule server API is the primary interface for collecting telemetry, tracking economy transactions, monitoring server health, querying retention cohorts, and managing event dispatch pipelines.



Initializes the analytics engine with user configuration. If already initialized, returns the existing singleton instance. When called from a client context (RunService:IsClient()), automatically redirects to the Client SDK.

AnalyticsModule.init(config: AnalyticsConfig?): AnalyticsInstance
Parameter Type Required Description
config AnalyticsConfig? No Optional configuration table overriding engine defaults.
Type Description
AnalyticsInstance The active singleton analytics manager.
local ReplicatedStorage = game:GetService("ReplicatedStorage")
local AnalyticsModule = require(ReplicatedStorage.AnalyticsModule)
local Analytics = AnalyticsModule.init({
debugMode = true,
flushIntervalSeconds = 15,
autoTrackDemographics = true,
})

Forces an immediate synchronous-style flush of the in-memory buffer queue to all registered exporters.

Analytics:Flush(): ()
  • Flushes are invoked automatically by the background worker at flushIntervalSeconds and upon server shutdown inside game:BindToClose.
  • Call this method before executing operations where pending events must be dispatched immediately (e.g. before triggering a teleport).
-- Manually flush all queued telemetry before teleporting a group
Analytics:Flush()
TeleportService:TeleportPartyAsync(placeId, players)

Dispatches a custom telemetry event into the pipeline. If a Player instance is supplied, automatically enriches the event with their UserId and active SessionId.

Analytics:TrackEvent(player: Player?, eventName: string, data: { [string]: any }?): ()
Parameter Type Required Description
player Player? No Optional player associated with the action. If nil, the event is logged as a server-level action.
eventName string Yes Alphanumeric identifier for the event (e.g. "BossDefeated", "DialogueSkipped").
data { [string]: any }? No Dictionary of custom key-value pairs (strings, numbers, booleans, nested dictionaries).
{
"name": "BossDefeated",
"category": "custom",
"timestamp": 1727790000,
"userId": 12345678,
"sessionId": "4a7f05b3-3a9d-4762-b91c-7f516a249d41",
"data": {
"bossId": "Dragon_01",
"difficulty": "Hard",
"rewardsGranted": 3
}
}
Analytics:TrackEvent(player, "CraftingCompleted", {
recipeId = "IronSword",
successRate = 0.95,
materialsConsumed = { "IronOre", "Wood" },
})

Convenience wrapper to increment a named numeric metric counter. Formats the internal event name as Metric_<metricName> with { incrementBy = amount }.

Analytics:Increment(metricName: string, amount: number?, tags: { [string]: any }?): ()
Parameter Type Default Description
metricName string — The metric to increment (e.g. "CoinsMined", "PortalsOpened").
amount number? 1 Amount to add to the counter. Defaults to 1.
tags { [string]: any }? {} Optional metadata tags for grouping or cohort filtering.
-- Increment gold mined metric by 25 with biome tag
Analytics:Increment("GoldMined", 25, { biome = "CrystalCaverns" })

Measures the elapsed execution time of an operation or gameplay phase. Returns a stop callback function that finishes the timer, calculates the elapsed time in seconds, dispatches a Timer_<timerName> event, and returns the duration.

Analytics:StartTimer(player: Player?, timerName: string): () -> number
Parameter Type Required Description
player Player? No Optional player performing the timed action.
timerName string Yes Identifier for the action (e.g. "DungeonGeneration", "RoundDuration").
Type Description
() -> number Callback function. Calling this function concludes the measurement and returns the elapsed time in seconds (rounded to 2 decimal places).
local stopTimer = Analytics:StartTimer(player, "MatchDuration")
-- Later when the match concludes:
local elapsedSeconds = stopTimer()
print(string.format("Match lasted %.2f seconds", elapsedSeconds))

Records coordinates $(X, Y, Z)$ alongside custom metadata. Coordinates are automatically rounded to 1 decimal place to optimize compression and facilitate spatial aggregation.

Analytics:TrackSpatial(player: Player?, eventName: string, position: Vector3, data: { [string]: any }?): ()
Parameter Type Required Description
player Player? No Optional player associated with the location.
eventName string Yes Name of the spatial event (e.g. "ChestDiscovered", "TrapTriggered").
position Vector3 Yes World space 3D vector.
data { [string]: any }? No Additional contextual metadata.
local chestPosition = chestModel:GetPivot().Position
Analytics:TrackSpatial(player, "SecretFound", chestPosition, {
secretTier = "Mythic",
zone = "TempleRuins",
})

Safely awards a Roblox badge to a player. Automatically verifies ownership first using BadgeService:UserHasBadgeAsync to prevent duplicate API calls, catches network exceptions, and records progression telemetry.

Analytics:AwardBadge(playerOrUserId: Player | number, badgeId: number): (boolean, boolean, string?)
Parameter Type Required Description
playerOrUserId Player | number Yes Either a live Player instance or their numeric UserId.
badgeId number Yes Roblox Badge ID.
Position Type Description
1 boolean callOk: true if the engine call succeeded without error.
2 boolean wasAwarded: true if the badge was newly awarded; false if already owned or call failed.
3 string? errorMessage: Error description if the call failed or user already owned badge.
local ok, awarded, err = Analytics:AwardBadge(player, 212456789)
if awarded then
print("Player earned a new badge!")
elseif not ok then
warn("Failed to award badge: " .. tostring(err))
end

Manual recording hook for projects utilizing their own custom BadgeService wrapper.

Analytics:RecordBadgeAward(userId: number, badgeId: number, success: boolean, errorMessage: string?): ()
Parameter Type Required Description
userId number Yes Numeric player user ID.
badgeId number Yes Roblox Badge ID.
success boolean Yes Whether the badge was successfully granted.
errorMessage string? No Error message if the award failed.

Returns the total number of times a specific badge has been successfully awarded by this server.

Analytics:GetBadgeAwardCount(badgeId: number): number

Returns the aggregate count of all badges awarded across this server instance.

Analytics:GetTotalBadgesAwarded(): number

Tracks virtual currency or items granted to a player (quest payouts, daily rewards, leveling gifts, loot drops).

Analytics:RecordEconomySource(
playerOrUserId: Player | number,
currency: string,
amount: number,
itemType: string?,
itemId: string?
): ()
Parameter Type Required Description
playerOrUserId Player | number Yes Target player instance or user ID.
currency string Yes Currency name (e.g. "Gold", "Gems").
amount number Yes Amount of currency added.
itemType string? No Source category (e.g. "QuestReward", "DailyLogin").
itemId string? No Source identifier (e.g. "Quest_204").

Tracks virtual currency or items spent by a player (store purchases, weapon upgrades, cosmetic unlocks).

Analytics:RecordEconomySink(
playerOrUserId: Player | number,
currency: string,
amount: number,
itemType: string?,
itemId: string?
): ()
Parameter Type Required Description
playerOrUserId Player | number Yes Target player instance or user ID.
currency string Yes Currency name (e.g. "Gold", "Gems").
amount number Yes Amount of currency spent.
itemType string? No Sink category (e.g. "WeaponUpgrade", "ShopItem").
itemId string? No Sink identifier (e.g. "Sword_Tier3").

Retention methods require enableRetentionTracking = true (default: true) in your configuration.

Returns whether a player is visiting the game for the first time in their account history.

Analytics:IsNewPlayer(playerOrUserId: Player | number): boolean
Players.PlayerAdded:Connect(function(player)
-- Allow retention record to initialize
task.wait(0.5)
if Analytics:IsNewPlayer(player) then
print(player.Name .. " is a brand new player! Showing tutorial...")
TutorialManager:Start(player)
end
end)

Returns the player’s total lifetime visit count across all game sessions.

Analytics:GetTotalVisits(playerOrUserId: Player | number): number

Returns the total cumulative playtime (in seconds) across all previous and current sessions for this player.

Analytics:GetLifetimePlaytimeSeconds(playerOrUserId: Player | number): number

Calculates the average session length in seconds across all sessions completed on this server.

Analytics:GetAveragePlaytimeSeconds(): number

Returns the uptime of the current server in seconds since startup.

Analytics:GetServerUptimeSeconds(): number

Returns a live diagnostics snapshot of server memory, concurrency, and performance.

Analytics:GetServerHealth(): ServerHealthSnapshot?
type ServerHealthSnapshot = {
serverJobId: string,
placeId: number,
placeVersion: number,
uptimeSeconds: number,
playerCount: number,
peakPlayerCount: number,
memoryUsageMb: number,
averageHeartbeatFps: number,
timestamp: number,
}

Registers middleware into the synchronous event dispatch pipeline. Middleware functions can mutate event attributes or drop events by returning nil.

Analytics:Use(middleware: (event: TelemetryEvent) -> TelemetryEvent?): ()
-- Enrich all events with the game environment
Analytics:Use(function(event)
event.data.environment = "Production"
return event
end)
-- Drop spammy events
Analytics:Use(function(event)
if event.name == "RedundantPing" then
return nil -- Event dropped
end
return event
end)

Registers a telemetry exporter implementing the IExporter interface.

Analytics:AddExporter(exporter: IExporter): ()
local DiscordExporter = require(ServerScriptService.Exporters.DiscordExporter)
Analytics:AddExporter(DiscordExporter.new(webhookSecret))