Astro Leaderboard

Official Astro Leaderboard documentation for installing Roblox global rankings with OrderedDataStore values, player profiles, regional flags, currency styling and privacy controls.

On this page

Before you install

Install only one leaderboard edition in an experience. Astro Leaderboard and Astro Leaderboard Free each contain a complete runtime, stat observer, refresh loop and test command. If you are upgrading, remove the entire Free package and its board models before adding the paid edition.

The system stores global ranking snapshots. Your game must continue to save and load its main player stats through its own data service.

Installation

Place the supplied objects at these exact locations:

ServerScriptService
└── PaidLeaderboard
    ├── Config
    ├── LeaderboardService
    ├── Main
    └── NumberFormatter

Workspace
└── Leaderboard
    └── PaidLeaderboard

The required row path is:

Cube.Part.SurfaceGui.Placements.ScrollingFrame.Row_1.Frame

Each row keeps the Placement, Name, Amount, Country, Profile, FrontCurrency and BackCurrency objects supplied with the model. The profile picture remains at Profile.ProfileHolder.ProfileHere. Both currency containers keep a CurrencyText and CurrencyImage inside their ProfileHolder.

You can restyle, resize and rearrange these objects in Studio. Keep their names and hierarchy intact. Row_1 through Row_3 preserve their own designs, while Row_4 is the template for later placements.

First configuration

  1. Open ServerScriptService.PaidLeaderboard.Config.
  2. Give DataStore.Name a stable name for the board’s stat.
  3. Give Country.DataStoreName a suitable name for stored regional codes.
  4. Set Stat.Name and confirm the Workspace BoardPath.
  5. Configure profile, country and currency options.
  6. Replace TestCommand.AllowedUserIds with trusted tester IDs.
  7. Publish the experience before testing live OrderedDataStore data.

Connect a stat

The package reads a numeric ValueBase from player.leaderstats first, then falls back to a Player attribute when enabled. Names are case-sensitive.

player.leaderstats.Coins.Value = 500
player:SetAttribute("Coins", 500)

You can also use the server API with the board ID:

local Leaderboard = require(
    game.ServerScriptService.PaidLeaderboard.LeaderboardService
)

Leaderboard:SetPlayerStat(player, "Coins", 500)
Leaderboard:AddPlayerStat(player, "Coins", 25)
local coins = Leaderboard:GetPlayerStat(player, "Coins")

The methods are server-only. SetPlayerStat uses the configured leaderstat when present, otherwise it uses the Player attribute when allowed. GetPlayerStat returns nil when no numeric source is available.

Leaderboard:GetBoardIds(), Leaderboard:RefreshNow("Coins") and Leaderboard:RefreshNow() provide board discovery and manual refresh helpers. Manual refreshes read the current OrderedDataStore but do not skip pending buffered writes.

Profiles and flags

Set Profile.Enabled to control Roblox profile pictures. The supplied defaults request a headshot at 150 by 150 pixels. Disabling profiles hides the entire profile frame and avoids thumbnail requests.

Regional flags have one master switch and two independent positions:

Setting Result
Country.Enabled Enables or disables the regional feature
Country.ShowFlagInRow Shows the flag beside row content
Country.ShowFlagOnProfile Shows the flag in the profile area
Country.UnknownSymbol Fallback when no usable region is available

Either position, both positions or neither may be selected. A profile flag cannot appear when the full profile frame is disabled.

The service requests a connected player’s country or region only through Roblox LocalizationService. It does not use an external API, IP address, language or username. The result is the region Roblox reports for that session, not verified nationality.

When StoreResolvedCountries is enabled, the service can save a two-letter code for use after that player leaves. Offline users without a saved code show the configured fallback. Paid boards may share one country DataStore because those codes are stored by user ID rather than ranking stat.

Privacy controls

Three settings control whether a regional result is shown:

Country = {
    AnonymousByDefault = false,
    AnonymousUserIds = {},
    PrivacyAttribute = "LeaderboardCountryAnonymous",
}

AnonymousByDefault = true makes every player anonymous. IDs inside AnonymousUserIds are also hidden. For a player-controlled privacy option, connect your settings interface to the configured Player attribute:

player:SetAttribute("LeaderboardCountryAnonymous", true)

When the attribute is true, the display uses the fallback instead of a flag and removes the stored country code when writes are permitted. Set it to false to opt the player back in. Review Roblox policy and the privacy requirements that apply to your experience before enabling location-derived presentation.

Currency display

Currency is configured separately inside each Board({...}) entry and is disabled by default.

Currency = {
    Enabled = true,
    DisplayType = "Text",
    Position = "Front",
    CurrencyName = "$",
}

DisplayType accepts Text or Image. Position accepts Front or Back. Text mode uses CurrencyName, which may be a symbol or a short word such as Coins. For image mode, set the selected CurrencyImage.Image asset in Studio. Colours, fonts, transparency and sizing also remain Studio design settings.

Only the selected currency control and position are visible. Currency is hidden on empty rows and both containers remain hidden when the feature is disabled.

Multiple boards

Copy the short Board({...}) entry in Config.Boards and duplicate the supplied model. Every board needs a unique Id and BoardPath. Different stats need different score DataStore names.

Board({
    Id = "Wins",
    BoardPath = { "Leaderboard", "TopWins" },
    Title = "Top Wins",
    Stat = { Name = "Wins" },
    DataStore = { Name = "Leaderboard_Wins_v1" },
    Profile = { Enabled = true },
    Country = {
        ShowFlagInRow = false,
        ShowFlagOnProfile = true,
    },
})

Board entries inherit BOARD_DEFAULTS, so include only settings that differ. Two visual boards may share a score DataStore only when they intentionally show the same stat. They may share the country DataStore regardless of stat.

Practical three-board pattern

A full experience can use separate boards for best win streak, total wins and coins. Give each stat its own board ID, Workspace path and OrderedDataStore name. Descending order suits all three. Compact number formatting works well for coins, while wins and streaks can stay as whole values. Protect lifetime wins and best streak in your main data service with maximum-value updates so delayed or older values cannot lower them.

Testing and support

In a Studio playtest, /lb load 100 fills the display with temporary values, public Roblox usernames and current public thumbnails. It does not write fake ranking data. Offline test profiles show the regional fallback because Roblox does not expose a real country for them. Run /lb clear to restore real data.

Only IDs in TestCommand.AllowedUserIds may use the command. Replace the included ID with your own trusted tester IDs, or disable the command when testing is complete.

Keep ReadInStudio and WriteInStudio false unless production access is intentional. Stat changes are buffered by WriteFlushDelay, then become visible after the next Refresh.Interval. Setup problems are reported once in Output, including missing board paths, row templates, profile objects, currency objects and incompatible flag settings. Fix the first warning, then restart the playtest.