@babylonjs-toolkit/server 0.0.0-stage → 9.35.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (236) hide show
  1. package/CUSTOM.md +1690 -0
  2. package/DEPLOY.md +2012 -0
  3. package/README.md +1081 -2
  4. package/lib/AbuseLimits.d.ts +64 -0
  5. package/lib/AbuseLimits.js +121 -0
  6. package/lib/Authentication.d.ts +86 -0
  7. package/lib/Authentication.js +272 -0
  8. package/lib/BootSessionOwner.d.ts +86 -0
  9. package/lib/BootSessionOwner.js +116 -0
  10. package/lib/ColyseusLoggerAdapter.d.ts +32 -0
  11. package/lib/ColyseusLoggerAdapter.js +73 -0
  12. package/lib/DedicatedSceneRegistry.d.ts +52 -0
  13. package/lib/DedicatedSceneRegistry.js +74 -0
  14. package/lib/DedicatedSession.d.ts +152 -0
  15. package/lib/DedicatedSession.js +173 -0
  16. package/lib/DualTransport.d.ts +112 -0
  17. package/lib/DualTransport.js +197 -0
  18. package/lib/GameServer.d.ts +64 -0
  19. package/lib/GameServer.js +647 -0
  20. package/lib/GameServerConfig.d.ts +387 -0
  21. package/lib/GameServerConfig.js +1059 -0
  22. package/lib/GameServerLobbyRoom.d.ts +33 -0
  23. package/lib/GameServerLobbyRoom.js +56 -0
  24. package/lib/GameServerLogger.d.ts +111 -0
  25. package/lib/GameServerLogger.js +190 -0
  26. package/lib/GameServerMetrics.d.ts +158 -0
  27. package/lib/GameServerMetrics.js +276 -0
  28. package/lib/GameServerState.d.ts +164 -0
  29. package/lib/GameServerState.js +26 -0
  30. package/lib/HeadlessRuntime.d.ts +316 -0
  31. package/lib/HeadlessRuntime.js +380 -0
  32. package/lib/JoinGate.d.ts +34 -0
  33. package/lib/JoinGate.js +221 -0
  34. package/lib/NetworkAddresses.d.ts +33 -0
  35. package/lib/NetworkAddresses.js +90 -0
  36. package/lib/PlayerTokens.d.ts +17 -0
  37. package/lib/PlayerTokens.js +24 -0
  38. package/lib/RoomServerTransport.d.ts +73 -0
  39. package/lib/RoomServerTransport.js +90 -0
  40. package/lib/ServerEndpoints.d.ts +133 -0
  41. package/lib/ServerEndpoints.js +247 -0
  42. package/lib/ServerInit.d.ts +28 -0
  43. package/lib/ServerInit.js +113 -0
  44. package/lib/SessionRoom.d.ts +391 -0
  45. package/lib/SessionRoom.js +930 -0
  46. package/lib/TlsCertificates.d.ts +35 -0
  47. package/lib/TlsCertificates.js +130 -0
  48. package/lib/admin/AccountRoutes.d.ts +8 -0
  49. package/lib/admin/AccountRoutes.js +502 -0
  50. package/lib/admin/AdminAccounts.d.ts +329 -0
  51. package/lib/admin/AdminAccounts.js +607 -0
  52. package/lib/admin/AdminApiRouter.d.ts +202 -0
  53. package/lib/admin/AdminApiRouter.js +465 -0
  54. package/lib/admin/AdminApiTypes.d.ts +1782 -0
  55. package/lib/admin/AdminApiTypes.js +4 -0
  56. package/lib/admin/AdminAudit.d.ts +113 -0
  57. package/lib/admin/AdminAudit.js +266 -0
  58. package/lib/admin/AdminCli.d.ts +7 -0
  59. package/lib/admin/AdminCli.js +351 -0
  60. package/lib/admin/AdminClock.d.ts +51 -0
  61. package/lib/admin/AdminClock.js +10 -0
  62. package/lib/admin/AdminConsole.d.ts +39 -0
  63. package/lib/admin/AdminConsole.js +325 -0
  64. package/lib/admin/AdminConstants.d.ts +147 -0
  65. package/lib/admin/AdminConstants.js +167 -0
  66. package/lib/admin/AdminCrypto.d.ts +19 -0
  67. package/lib/admin/AdminCrypto.js +29 -0
  68. package/lib/admin/AdminExtensionsHost.d.ts +176 -0
  69. package/lib/admin/AdminExtensionsHost.js +307 -0
  70. package/lib/admin/AdminPasswords.d.ts +33 -0
  71. package/lib/admin/AdminPasswords.js +92 -0
  72. package/lib/admin/AdminPermissions.d.ts +28 -0
  73. package/lib/admin/AdminPermissions.js +74 -0
  74. package/lib/admin/AdminRecords.d.ts +196 -0
  75. package/lib/admin/AdminRecords.js +3 -0
  76. package/lib/admin/AdminRequestBodies.d.ts +47 -0
  77. package/lib/admin/AdminRequestBodies.js +84 -0
  78. package/lib/admin/AdminRequestGate.d.ts +38 -0
  79. package/lib/admin/AdminRequestGate.js +59 -0
  80. package/lib/admin/AdminResponses.d.ts +103 -0
  81. package/lib/admin/AdminResponses.js +164 -0
  82. package/lib/admin/AdminServices.d.ts +99 -0
  83. package/lib/admin/AdminServices.js +4 -0
  84. package/lib/admin/AdminStaticFiles.d.ts +29 -0
  85. package/lib/admin/AdminStaticFiles.js +97 -0
  86. package/lib/admin/AdminStore.d.ts +152 -0
  87. package/lib/admin/AdminStore.js +46 -0
  88. package/lib/admin/AlertChannels.d.ts +43 -0
  89. package/lib/admin/AlertChannels.js +120 -0
  90. package/lib/admin/AlertEngine.d.ts +231 -0
  91. package/lib/admin/AlertEngine.js +681 -0
  92. package/lib/admin/AlertRoutes.d.ts +8 -0
  93. package/lib/admin/AlertRoutes.js +180 -0
  94. package/lib/admin/ApiKeyRoutes.d.ts +8 -0
  95. package/lib/admin/ApiKeyRoutes.js +53 -0
  96. package/lib/admin/ApiKeys.d.ts +63 -0
  97. package/lib/admin/ApiKeys.js +167 -0
  98. package/lib/admin/AuditRoutes.d.ts +8 -0
  99. package/lib/admin/AuditRoutes.js +106 -0
  100. package/lib/admin/AuthToolRoutes.d.ts +13 -0
  101. package/lib/admin/AuthToolRoutes.js +164 -0
  102. package/lib/admin/BanList.d.ts +87 -0
  103. package/lib/admin/BanList.js +152 -0
  104. package/lib/admin/CborDecoder.d.ts +18 -0
  105. package/lib/admin/CborDecoder.js +201 -0
  106. package/lib/admin/ColyseusCloudClient.d.ts +313 -0
  107. package/lib/admin/ColyseusCloudClient.js +272 -0
  108. package/lib/admin/ColyseusCloudRoutes.d.ts +8 -0
  109. package/lib/admin/ColyseusCloudRoutes.js +91 -0
  110. package/lib/admin/ColyseusCloudService.d.ts +180 -0
  111. package/lib/admin/ColyseusCloudService.js +476 -0
  112. package/lib/admin/ColyseusCloudSettings.d.ts +16 -0
  113. package/lib/admin/ColyseusCloudSettings.js +29 -0
  114. package/lib/admin/ColyseusCloudViews.d.ts +105 -0
  115. package/lib/admin/ColyseusCloudViews.js +371 -0
  116. package/lib/admin/CommonPasswords.d.ts +6 -0
  117. package/lib/admin/CommonPasswords.js +19 -0
  118. package/lib/admin/ConfigOverrides.d.ts +174 -0
  119. package/lib/admin/ConfigOverrides.js +406 -0
  120. package/lib/admin/ConfigRoutes.d.ts +8 -0
  121. package/lib/admin/ConfigRoutes.js +91 -0
  122. package/lib/admin/ConsoleSessions.d.ts +112 -0
  123. package/lib/admin/ConsoleSessions.js +201 -0
  124. package/lib/admin/DedicatedRoutes.d.ts +21 -0
  125. package/lib/admin/DedicatedRoutes.js +254 -0
  126. package/lib/admin/ExtensionRoutes.d.ts +8 -0
  127. package/lib/admin/ExtensionRoutes.js +145 -0
  128. package/lib/admin/FileAdminStore.d.ts +157 -0
  129. package/lib/admin/FileAdminStore.js +349 -0
  130. package/lib/admin/FleetDirectory.d.ts +323 -0
  131. package/lib/admin/FleetDirectory.js +489 -0
  132. package/lib/admin/FleetLeader.d.ts +43 -0
  133. package/lib/admin/FleetLeader.js +89 -0
  134. package/lib/admin/FleetRoutes.d.ts +55 -0
  135. package/lib/admin/FleetRoutes.js +465 -0
  136. package/lib/admin/HealthWarnings.d.ts +10 -0
  137. package/lib/admin/HealthWarnings.js +95 -0
  138. package/lib/admin/LeaderboardRoutes.d.ts +8 -0
  139. package/lib/admin/LeaderboardRoutes.js +569 -0
  140. package/lib/admin/LogBuffer.d.ts +60 -0
  141. package/lib/admin/LogBuffer.js +92 -0
  142. package/lib/admin/LogRedaction.d.ts +15 -0
  143. package/lib/admin/LogRedaction.js +72 -0
  144. package/lib/admin/LogRoutes.d.ts +45 -0
  145. package/lib/admin/LogRoutes.js +307 -0
  146. package/lib/admin/MaintenanceMode.d.ts +41 -0
  147. package/lib/admin/MaintenanceMode.js +74 -0
  148. package/lib/admin/MaintenanceWindows.d.ts +91 -0
  149. package/lib/admin/MaintenanceWindows.js +207 -0
  150. package/lib/admin/MetricsRoutes.d.ts +8 -0
  151. package/lib/admin/MetricsRoutes.js +209 -0
  152. package/lib/admin/MetricsSampler.d.ts +124 -0
  153. package/lib/admin/MetricsSampler.js +211 -0
  154. package/lib/admin/OneTimeCodes.d.ts +60 -0
  155. package/lib/admin/OneTimeCodes.js +162 -0
  156. package/lib/admin/OpenIdConnect.d.ts +146 -0
  157. package/lib/admin/OpenIdConnect.js +335 -0
  158. package/lib/admin/Passkeys.d.ts +130 -0
  159. package/lib/admin/Passkeys.js +432 -0
  160. package/lib/admin/PlayerRoutes.d.ts +20 -0
  161. package/lib/admin/PlayerRoutes.js +676 -0
  162. package/lib/admin/RedisAdminStore.d.ts +114 -0
  163. package/lib/admin/RedisAdminStore.js +258 -0
  164. package/lib/admin/RolloutCoordinator.d.ts +99 -0
  165. package/lib/admin/RolloutCoordinator.js +321 -0
  166. package/lib/admin/ServerEvents.d.ts +57 -0
  167. package/lib/admin/ServerEvents.js +89 -0
  168. package/lib/admin/SessionRoutes.d.ts +113 -0
  169. package/lib/admin/SessionRoutes.js +386 -0
  170. package/lib/admin/UserRoutes.d.ts +8 -0
  171. package/lib/admin/UserRoutes.js +214 -0
  172. package/lib/cli.d.ts +2 -0
  173. package/lib/cli.js +221 -0
  174. package/lib/console/assets/index-CI5N7c-T.js +21 -0
  175. package/lib/console/assets/index-DPitvzLp.css +1 -0
  176. package/lib/console/favicon.svg +1 -0
  177. package/lib/console/index.html +16 -0
  178. package/lib/discord/DiscordOAuth.d.ts +57 -0
  179. package/lib/discord/DiscordOAuth.js +127 -0
  180. package/lib/discord/DiscordSessions.d.ts +79 -0
  181. package/lib/discord/DiscordSessions.js +135 -0
  182. package/lib/discord/DiscordSignInConstants.d.ts +54 -0
  183. package/lib/discord/DiscordSignInConstants.js +55 -0
  184. package/lib/discord/DiscordSignInRoutes.d.ts +51 -0
  185. package/lib/discord/DiscordSignInRoutes.js +359 -0
  186. package/lib/index.d.ts +24 -0
  187. package/lib/index.js +18 -0
  188. package/lib/leaderboards/FileLeaderboardRankStore.d.ts +293 -0
  189. package/lib/leaderboards/FileLeaderboardRankStore.js +808 -0
  190. package/lib/leaderboards/LeaderboardConstants.d.ts +63 -0
  191. package/lib/leaderboards/LeaderboardConstants.js +70 -0
  192. package/lib/leaderboards/LeaderboardError.d.ts +15 -0
  193. package/lib/leaderboards/LeaderboardError.js +20 -0
  194. package/lib/leaderboards/LeaderboardIdentity.d.ts +44 -0
  195. package/lib/leaderboards/LeaderboardIdentity.js +72 -0
  196. package/lib/leaderboards/LeaderboardPublicApi.d.ts +17 -0
  197. package/lib/leaderboards/LeaderboardPublicApi.js +389 -0
  198. package/lib/leaderboards/LeaderboardRankStore.d.ts +296 -0
  199. package/lib/leaderboards/LeaderboardRankStore.js +18 -0
  200. package/lib/leaderboards/LeaderboardRules.d.ts +122 -0
  201. package/lib/leaderboards/LeaderboardRules.js +472 -0
  202. package/lib/leaderboards/LeaderboardScheduler.d.ts +43 -0
  203. package/lib/leaderboards/LeaderboardScheduler.js +103 -0
  204. package/lib/leaderboards/LeaderboardService.d.ts +669 -0
  205. package/lib/leaderboards/LeaderboardService.js +1667 -0
  206. package/lib/leaderboards/LeaderboardTransfer.d.ts +35 -0
  207. package/lib/leaderboards/LeaderboardTransfer.js +580 -0
  208. package/lib/leaderboards/RedisLeaderboardRankStore.d.ts +282 -0
  209. package/lib/leaderboards/RedisLeaderboardRankStore.js +691 -0
  210. package/package.json +64 -4
  211. package/templates/init/Caddyfile +6 -0
  212. package/templates/init/DEPLOY.md +233 -0
  213. package/templates/init/Dockerfile +12 -0
  214. package/templates/init/app.json +21 -0
  215. package/templates/init/aws/README.md +118 -0
  216. package/templates/init/aws/ecs-fargate-alb.yml +207 -0
  217. package/templates/init/aws/ecs-fargate-nlb-quic.yml +210 -0
  218. package/templates/init/babylon-game-server.config.mjs +158 -0
  219. package/templates/init/colyseus-cloud/README.md +133 -0
  220. package/templates/init/colyseus-cloud/babylon-game-server.config.mjs +36 -0
  221. package/templates/init/colyseus-cloud/ecosystem.config.cjs +35 -0
  222. package/templates/init/colyseus-cloud/gitignore +6 -0
  223. package/templates/init/colyseus-cloud/package.json +15 -0
  224. package/templates/init/digitalocean-app.yaml +30 -0
  225. package/templates/init/docker-compose.full.yml +45 -0
  226. package/templates/init/docker-compose.websocket.yml +41 -0
  227. package/templates/init/fly.toml +56 -0
  228. package/templates/init/heroku.yml +11 -0
  229. package/templates/init/kubernetes/deployment.yaml +71 -0
  230. package/templates/init/kubernetes/redis.yaml +73 -0
  231. package/templates/init/kubernetes/service.yaml +24 -0
  232. package/templates/init/monitoring/grafana-dashboard.json +539 -0
  233. package/templates/init/monitoring/prometheus-alerts.yml +51 -0
  234. package/templates/init/monitoring/prometheus-scrape.yml +17 -0
  235. package/templates/init/railway.json +13 -0
  236. package/templates/init/render.yaml +19 -0
@@ -0,0 +1,669 @@
1
+ import type { LeaderboardActivityView, LeaderboardAroundPage, LeaderboardBoardDefinition, LeaderboardBoardDetailView, LeaderboardBoardSummaryView, LeaderboardEntriesPage, LeaderboardEntryView, LeaderboardPlayerAdminView, LeaderboardPlayerDetailView, LeaderboardPlayerSession, LeaderboardPlayerView, LeaderboardPublicBoardView, LeaderboardRemovedEntryView, LeaderboardRules, LeaderboardRulesView, LeaderboardSeasonView, LeaderboardStatusView, LeaderboardSubmissionRequest, LeaderboardSubmissionResponse, LeaderboardTarget, LeaderboardTargetEntry } from "../admin/AdminApiTypes.js";
2
+ import type { AdminClock } from "../admin/AdminClock.js";
3
+ import type { PlayerSessionEvent } from "../admin/AdminRecords.js";
4
+ import { type AdminStore, type StoredDocument } from "../admin/AdminStore.js";
5
+ import type { GameServerConfig } from "../GameServerConfig.js";
6
+ import type { GameServerStateValues } from "../GameServerState.js";
7
+ import type { LeaderboardPlayerRecord, LeaderboardRankStore } from "./LeaderboardRankStore.js";
8
+ /** Who is calling, after authentication. */
9
+ export interface LeaderboardCaller {
10
+ /** The auth user id when the server's auth yielded one, else null. */
11
+ userId: string | null;
12
+ /** The display-name claim of an auth user (name or preferred_username), else null. */
13
+ userDisplayName: string | null;
14
+ /** The avatar claim of an auth user (string), else null. */
15
+ userAvatar: string | null;
16
+ /** True when the caller's session owns the name (claim name_managed: true), so renames are refused. */
17
+ isNameManaged: boolean;
18
+ /** The anonymous player key from the body, else null. */
19
+ playerKey: string | null;
20
+ /** The normalized client address. */
21
+ clientAddress: string;
22
+ }
23
+ /** What the Discord session exchange asks of the leaderboards (discord-sign-in D16). */
24
+ export interface LeaderboardUserClaim {
25
+ /** The auth user id (discord:<id>). */
26
+ userId: string;
27
+ /** The display name from the sign-in. */
28
+ displayName: string;
29
+ /** The avatar claim, or null. */
30
+ avatar: string | null;
31
+ /** The browser's anonymous player key, or null when it has none. */
32
+ anonymousPlayerKey: string | null;
33
+ }
34
+ /** The outcome of a claim. */
35
+ export interface LeaderboardUserClaimResult {
36
+ /** The user's player id (user:discord:<id>). */
37
+ playerId: string;
38
+ /** True when an anonymous history was moved onto the new player. */
39
+ merged: boolean;
40
+ }
41
+ /** Options of LeaderboardService.open. */
42
+ export interface LeaderboardServiceOptions {
43
+ /** The resolved config. */
44
+ config: GameServerConfig;
45
+ /**
46
+ * The server state: the service reads only `metrics` and sets `onLeaderboardSessionPresence`. Tests pass a plain
47
+ * object `{ config, metrics: null, onLeaderboardSessionPresence: null }`.
48
+ */
49
+ state: GameServerStateValues;
50
+ /** The admin store (boards, rules, activity). */
51
+ adminStore: AdminStore;
52
+ /** The rank store (rankings, players, rates, presence). */
53
+ rankStore: LeaderboardRankStore;
54
+ /** The clock of every time the service writes and every timer (tests pass createManualClock()). */
55
+ clock: AdminClock;
56
+ /** This process's id for the scheduler lease (matchMaker.processId, read lazily). */
57
+ processId: () => string;
58
+ /** Milliseconds between scheduler ticks. */
59
+ schedulerTickMs: number;
60
+ }
61
+ /** A board as stored in the admin store collection "leaderboards" (document id = boardId). */
62
+ export interface LeaderboardBoardRecord {
63
+ /** What an admin defined. */
64
+ definition: LeaderboardBoardDefinition;
65
+ /** The season new scores go to. */
66
+ currentSeasonId: number;
67
+ /** Every season still kept, oldest first. */
68
+ seasons: LeaderboardSeasonView[];
69
+ /** ISO time of the next scheduled reset, or null. */
70
+ nextResetAt: string | null;
71
+ /** ISO creation time. */
72
+ createdAt: string;
73
+ }
74
+ /** A server-trust submission (admin route `leaderboards/submit`, DR §6): the player is named, not resolved. */
75
+ export type LeaderboardServerSubmissionRequest = LeaderboardSubmissionRequest & {
76
+ /** The player the scores belong to. */
77
+ playerId: string;
78
+ /** The name of a manual player created when playerId is unknown. */
79
+ displayName?: string;
80
+ };
81
+ /** Boards, seasons, rules, players, submissions, reads, activity, status and presence (D4). */
82
+ export declare class LeaderboardService {
83
+ /** The options it was opened with. */
84
+ private readonly options;
85
+ /** The cached boards, or null. */
86
+ private boardCache;
87
+ /** The cached rules, or null. */
88
+ private rulesCache;
89
+ /** Cached top-N pages by `rankKeyText|offset|limit`. */
90
+ private readonly readCache;
91
+ /** The definitions-file problem found by the last start, or null. */
92
+ private definitionsProblem;
93
+ /** The scheduler while started, or null. */
94
+ private scheduler;
95
+ /**
96
+ * Creates the service; open() is the public way.
97
+ * @param options The options.
98
+ */
99
+ private constructor();
100
+ /**
101
+ * Opens the service (nothing runs until start()).
102
+ * @param options The stores, state, clock and scheduler settings.
103
+ * @returns The service.
104
+ */
105
+ static open(options: LeaderboardServiceOptions): Promise<LeaderboardService>;
106
+ /** The admin store and rank store, for LeaderboardTransfer (T6). */
107
+ get stores(): {
108
+ adminStore: AdminStore;
109
+ rankStore: LeaderboardRankStore;
110
+ };
111
+ /**
112
+ * Imports the definitions file, hides anonymous entries when only signed-in players may submit, starts listening for
113
+ * session presence and starts the scheduler.
114
+ */
115
+ start(): Promise<void>;
116
+ /** Stops the scheduler, stops listening for session presence and closes the rank store. */
117
+ stop(): Promise<void>;
118
+ /**
119
+ * Lists every board document (cached for LEADERBOARD_DEFINITION_CACHE_MS), sorted by board id.
120
+ * @returns The documents.
121
+ */
122
+ listBoardRecords(): Promise<StoredDocument<LeaderboardBoardRecord>[]>;
123
+ /**
124
+ * Reads one board document fresh from the admin store.
125
+ * @param boardId The board.
126
+ * @returns The document.
127
+ * @throws LeaderboardError 404 unknownBoard when it does not exist.
128
+ */
129
+ getBoardRecord(boardId: string): Promise<StoredDocument<LeaderboardBoardRecord>>;
130
+ /**
131
+ * The public boards as game clients see them.
132
+ * @returns The boards, sorted by board id.
133
+ */
134
+ listPublicBoards(): Promise<LeaderboardPublicBoardView[]>;
135
+ /**
136
+ * A board's console summary: definition, seasons, live entries of the current season and the last submission.
137
+ * @param stored The board document.
138
+ * @returns The summary.
139
+ */
140
+ summarizeBoard(stored: StoredDocument<LeaderboardBoardRecord>): Promise<LeaderboardBoardSummaryView>;
141
+ /**
142
+ * A board's detail view: its summary and every variant of one season with its top entry.
143
+ * @param boardId The board.
144
+ * @param seasonId The season, or null for the current one.
145
+ * @returns The detail view.
146
+ */
147
+ describeBoard(boardId: string, seasonId: number | null): Promise<LeaderboardBoardDetailView>;
148
+ /**
149
+ * Creates a board with season 1.
150
+ * @param definition The definition (any JSON; validated).
151
+ * @returns The new board's summary.
152
+ * @throws LeaderboardError 400 invalidRequest for an invalid definition; AdminConflictError when the id exists.
153
+ */
154
+ createBoard(definition: LeaderboardBoardDefinition): Promise<LeaderboardBoardSummaryView>;
155
+ /**
156
+ * Updates a board's definition. Changing sortOrder, scoreFormat or keepPolicy while the current season has entries
157
+ * needs startNewSeason (D17); startNewSeason always starts the next season in the same write.
158
+ * @param boardId The board.
159
+ * @param definition The new definition (its boardId must match).
160
+ * @param revision The revision the editor read.
161
+ * @param startNewSeason True to start the next season.
162
+ * @returns The updated summary.
163
+ * @throws LeaderboardError 400 for an invalid definition, 409 for a ranking change that needs a new season;
164
+ * AdminConflictError for a stale revision.
165
+ */
166
+ updateBoard(boardId: string, definition: LeaderboardBoardDefinition, revision: number, startNewSeason: boolean): Promise<LeaderboardBoardSummaryView>;
167
+ /**
168
+ * Creates a copy of a board's definition under a new id (no entries).
169
+ * @param boardId The source board.
170
+ * @param newBoardId The new id.
171
+ * @param displayName The new name.
172
+ * @returns The new board's summary.
173
+ */
174
+ duplicateBoard(boardId: string, newBoardId: string, displayName: string): Promise<LeaderboardBoardSummaryView>;
175
+ /**
176
+ * Deletes a board and every ranking of every season (activity records stay, DR §15).
177
+ * @param boardId The board.
178
+ */
179
+ deleteBoard(boardId: string): Promise<void>;
180
+ /**
181
+ * Ends the current season and starts the next (compare-and-set, retried on conflict). A scheduled reset that finds
182
+ * the board already reset by another writer returns without resetting again.
183
+ * @param boardId The board.
184
+ * @param trigger "admin" from the console, "schedule" from the scheduler.
185
+ * @returns The board's summary.
186
+ * @throws LeaderboardError 409 for a board that never resets.
187
+ */
188
+ resetSeason(boardId: string, trigger: "admin" | "schedule"): Promise<LeaderboardBoardSummaryView>;
189
+ /**
190
+ * Deletes an archived season's rankings and drops it from the board's season list.
191
+ * @param boardId The board.
192
+ * @param seasonId The season.
193
+ * @returns How many entries were deleted.
194
+ * @throws LeaderboardError 409 for the current season, 404 for a season the board does not keep.
195
+ */
196
+ deleteSeason(boardId: string, seasonId: number): Promise<number>;
197
+ /**
198
+ * A board's seasons, oldest first.
199
+ * @param boardId The board.
200
+ * @param audience "public" hides hidden boards (404).
201
+ * @returns The seasons.
202
+ */
203
+ listSeasons(boardId: string, audience: "public" | "admin"): Promise<LeaderboardSeasonView[]>;
204
+ /**
205
+ * The rules in force, the defaults and the stored revision (0 while the defaults apply).
206
+ * @returns The rules view.
207
+ */
208
+ getRulesView(): Promise<LeaderboardRulesView>;
209
+ /**
210
+ * Saves new rules.
211
+ * @param rules The rules (any JSON; validated).
212
+ * @param revision The revision the editor read (0 while the defaults apply).
213
+ * @returns The new rules view.
214
+ * @throws LeaderboardError 400 for invalid rules; AdminConflictError for a stale revision.
215
+ */
216
+ updateRules(rules: LeaderboardRules, revision: number): Promise<LeaderboardRulesView>;
217
+ /**
218
+ * Opens a player session (POST players): the auth user's player (created on first use), the player of a valid key,
219
+ * or a new anonymous player with its one-time key.
220
+ * @param caller The caller.
221
+ * @returns The player and, only for a new anonymous player, its key.
222
+ * @throws LeaderboardError 401 invalidPlayer for a wrong key, 429 rateLimited over identitiesPerHourPerAddress.
223
+ */
224
+ openPlayerSession(caller: LeaderboardCaller): Promise<LeaderboardPlayerSession>;
225
+ /**
226
+ * Resolves the caller's player without creating an anonymous one: the auth user's player (its record is created on
227
+ * first use, D8) or the player of a valid key.
228
+ * @param caller The caller.
229
+ * @returns The player record.
230
+ * @throws LeaderboardError 401 invalidPlayer when there is no auth user and no valid key.
231
+ */
232
+ resolvePlayer(caller: LeaderboardCaller): Promise<LeaderboardPlayerRecord>;
233
+ /**
234
+ * The caller's own player (POST players/me).
235
+ * @param caller The caller.
236
+ * @returns The player.
237
+ * @throws LeaderboardError 401 invalidPlayer.
238
+ */
239
+ getOwnPlayer(caller: LeaderboardCaller): Promise<LeaderboardPlayerView>;
240
+ /**
241
+ * Erases the caller's own player and every entry of theirs (POST players/me/delete).
242
+ * @param caller The caller.
243
+ * @returns How many entries were deleted.
244
+ * @throws LeaderboardError 401 invalidPlayer.
245
+ */
246
+ eraseOwnPlayer(caller: LeaderboardCaller): Promise<number>;
247
+ /**
248
+ * Gives a signed-in user their player at sign-in (D16): an existing player gets its name and avatar refreshed and
249
+ * nothing is merged; a new one is created and, when a valid anonymous key is sent, that anonymous player's history
250
+ * is merged into it (the anonymous player is erased by the merge).
251
+ * @param claim The user and the browser's anonymous key.
252
+ * @returns The player id and whether a merge happened.
253
+ */
254
+ claimUserPlayer(claim: LeaderboardUserClaim): Promise<LeaderboardUserClaimResult>;
255
+ /**
256
+ * Fills each entry's avatar from its player's record (only user: players can have one).
257
+ * @param entries The entries of one public read.
258
+ * @returns New entry objects with avatar set (null when the player has none).
259
+ */
260
+ attachAvatars(entries: LeaderboardEntryView[]): Promise<LeaderboardEntryView[]>;
261
+ /**
262
+ * Consumes one public read of an address against readsPerMinutePerAddress (D19 read limit scope).
263
+ * @param clientAddress The caller's address.
264
+ * @throws LeaderboardError 429 rateLimited.
265
+ */
266
+ consumeReadRate(clientAddress: string): Promise<void>;
267
+ /**
268
+ * Renames the caller's own player (POST players/me/name) with the current rules' blocked words.
269
+ * @param caller The caller.
270
+ * @param displayName The new name (any JSON; cleaned).
271
+ * @returns The player.
272
+ * @throws LeaderboardError 403 nameManaged for a signed-in caller whose session owns the name, 400 nameInvalid or
273
+ * nameBlocked, 401 invalidPlayer.
274
+ */
275
+ renameOwnPlayer(caller: LeaderboardCaller, displayName: unknown): Promise<LeaderboardPlayerView>;
276
+ /**
277
+ * Runs the submission pipeline (DR §10) in its binding order: request shape, score count, player, rate limits, trust,
278
+ * then per score board, variant, score, trust, metadata and write, each recorded in activity.
279
+ * @param caller The caller.
280
+ * @param request The envelope (a LeaderboardServerSubmissionRequest for source "server").
281
+ * @param source "public" from the public API, "server" from the admin route (server trust).
282
+ * @returns The per-score results.
283
+ * @throws LeaderboardError 400 invalidRequest or tooManyScores, 401 invalidPlayer, 403 signInRequired (a public
284
+ * caller with no auth user id while leaderboards.signedInPlayersOnly is on), 429 rateLimited.
285
+ */
286
+ submit(caller: LeaderboardCaller, request: LeaderboardSubmissionRequest, source: "public" | "server"): Promise<LeaderboardSubmissionResponse>;
287
+ /**
288
+ * Reads a page of one ranking (top-N reads are cached for LEADERBOARD_READ_CACHE_MS).
289
+ * @param boardId The board.
290
+ * @param variant The variant (null or {} without dimensions).
291
+ * @param seasonId The season, or null for the current one.
292
+ * @param offset Zero-based index of the first entry.
293
+ * @param limit Most entries.
294
+ * @param audience "public" hides hidden boards and checks variant values; "admin" also reads retired values.
295
+ * @returns The page.
296
+ */
297
+ readEntries(boardId: string, variant: Record<string, string> | null, seasonId: number | null, offset: number, limit: number, audience: "public" | "admin"): Promise<LeaderboardEntriesPage>;
298
+ /**
299
+ * Finds entries of one ranking by name or player id (console search).
300
+ * @param boardId The board.
301
+ * @param variantKey The variant key.
302
+ * @param seasonId The season.
303
+ * @param text The text.
304
+ * @returns The matches as a page.
305
+ */
306
+ searchEntries(boardId: string, variantKey: string, seasonId: number, text: string): Promise<LeaderboardEntriesPage>;
307
+ /**
308
+ * Reads the window around a player's entry.
309
+ * @param boardId The board.
310
+ * @param variant The variant.
311
+ * @param seasonId The season, or null for the current one.
312
+ * @param playerId The player.
313
+ * @param window Entries above and below.
314
+ * @returns The page with the player's rank (null without an entry).
315
+ */
316
+ readAround(boardId: string, variant: Record<string, string> | null, seasonId: number | null, playerId: string, window: number): Promise<LeaderboardAroundPage>;
317
+ /**
318
+ * Reads a player's entry in each of several rankings.
319
+ * @param playerId The player.
320
+ * @param targets The rankings.
321
+ * @returns One answer per target, in order.
322
+ */
323
+ readTargets(playerId: string, targets: LeaderboardTarget[]): Promise<LeaderboardTargetEntry[]>;
324
+ /**
325
+ * Reads the entries of named players in one ranking (friends lists).
326
+ * @param boardId The board.
327
+ * @param variant The variant.
328
+ * @param seasonId The season, or null for the current one.
329
+ * @param playerIds The players.
330
+ * @returns The entries they have, by rank.
331
+ */
332
+ readPlayersEntries(boardId: string, variant: Record<string, string> | null, seasonId: number | null, playerIds: string[]): Promise<LeaderboardEntryView[]>;
333
+ /**
334
+ * The removed entries of one ranking, newest removal first.
335
+ * @param boardId The board.
336
+ * @param variantKey The variant key.
337
+ * @param seasonId The season.
338
+ * @returns The removed entries (rank 0: they are not ranked).
339
+ */
340
+ readRemoved(boardId: string, variantKey: string, seasonId: number): Promise<LeaderboardRemovedEntryView[]>;
341
+ /**
342
+ * Removes a live entry from its ranking (D18).
343
+ * @param boardId The board.
344
+ * @param variantKey The variant key.
345
+ * @param seasonId The season.
346
+ * @param playerId The player.
347
+ * @param reason Why (shown in the console).
348
+ * @param actorName Who removed it.
349
+ * @throws LeaderboardError 404 when the player has no live entry.
350
+ */
351
+ removeEntry(boardId: string, variantKey: string, seasonId: number, playerId: string, reason: string, actorName: string): Promise<void>;
352
+ /**
353
+ * Puts a removed entry back into its ranking.
354
+ * @param boardId The board.
355
+ * @param variantKey The variant key.
356
+ * @param seasonId The season.
357
+ * @param playerId The player.
358
+ * @throws LeaderboardError 409 while the player has a live entry, 404 when nothing was removed.
359
+ */
360
+ restoreEntry(boardId: string, variantKey: string, seasonId: number, playerId: string): Promise<void>;
361
+ /**
362
+ * Corrects a live entry's score (keep policy latest, a fresh achieved time).
363
+ * @param boardId The board.
364
+ * @param variantKey The variant key.
365
+ * @param seasonId The season.
366
+ * @param playerId The player.
367
+ * @param score The corrected score.
368
+ * @returns The corrected entry with its new rank.
369
+ * @throws LeaderboardError 400 for a score the board refuses, 404 without a live entry.
370
+ */
371
+ correctEntry(boardId: string, variantKey: string, seasonId: number, playerId: string, score: number): Promise<LeaderboardEntryView>;
372
+ /**
373
+ * Adds an entry by hand at server trust: for a new manual player when playerId is null, else for that player.
374
+ * @param boardId The board.
375
+ * @param variant The variant.
376
+ * @param playerId The player, or null to create a manual player.
377
+ * @param displayName The new manual player's name (cleaned).
378
+ * @param score The score.
379
+ * @returns The entry with its rank.
380
+ * @throws LeaderboardError 400 for a bad variant, score or name, 404 for an unknown player.
381
+ */
382
+ addEntry(boardId: string, variant: Record<string, string> | null, playerId: string | null, displayName: string, score: number): Promise<LeaderboardEntryView>;
383
+ /**
384
+ * Renames a player and every entry of theirs.
385
+ * @param playerId The player.
386
+ * @param displayName The new name (cleaned with the blocked words).
387
+ * @returns The player.
388
+ * @throws LeaderboardError 400 nameInvalid or nameBlocked, 404 for an unknown player.
389
+ */
390
+ renamePlayer(playerId: string, displayName: string): Promise<LeaderboardPlayerAdminView>;
391
+ /**
392
+ * Hides a player (every live entry moves to removed with reason playerHidden, D18) or unhides them (those entries
393
+ * come back).
394
+ * @param playerId The player.
395
+ * @param hidden True to hide.
396
+ * @param actorName Who did it.
397
+ * @returns The player.
398
+ * @throws LeaderboardError 404 for an unknown player.
399
+ */
400
+ hidePlayer(playerId: string, hidden: boolean, actorName: string): Promise<LeaderboardPlayerAdminView>;
401
+ /**
402
+ * Merges one player into another (DR §15): per ranking of the source, the target board's keep policy decides — best
403
+ * keeps the better, latest the later, sum adds — then the source is erased.
404
+ * @param sourcePlayerId The player merged away.
405
+ * @param targetPlayerId The player kept.
406
+ * @returns The target's detail.
407
+ * @throws LeaderboardError 400 for the same player, 404 for an unknown one.
408
+ */
409
+ mergePlayers(sourcePlayerId: string, targetPlayerId: string): Promise<LeaderboardPlayerDetailView>;
410
+ /**
411
+ * Erases a player: every entry, live and removed, and the player record.
412
+ * @param playerId The player.
413
+ * @returns How many entries were deleted.
414
+ * @throws LeaderboardError 404 for a player with neither a record nor entries.
415
+ */
416
+ erasePlayer(playerId: string): Promise<number>;
417
+ /**
418
+ * A player and every entry of theirs across boards and seasons, live or removed.
419
+ * @param playerId The player.
420
+ * @returns The detail.
421
+ * @throws LeaderboardError 404 for an unknown player.
422
+ */
423
+ getPlayerDetail(playerId: string): Promise<LeaderboardPlayerDetailView>;
424
+ /**
425
+ * Finds players by name or id.
426
+ * @param text The text ("" lists any).
427
+ * @returns Up to 50 players.
428
+ */
429
+ searchPlayers(text: string): Promise<LeaderboardPlayerAdminView[]>;
430
+ /**
431
+ * Reads activity newest first, filtered by kind and board, scanning at most ACTIVITY_SCAN_LIMIT records (it may
432
+ * return fewer than limit; the console pages with the oldest sequence shown).
433
+ * @param kind The kind, or null for all.
434
+ * @param boardId The board, or null for all.
435
+ * @param beforeSequence Only records older than this sequence, or null.
436
+ * @param limit Most records.
437
+ * @param includeAddresses True to keep client addresses (players.viewAddresses).
438
+ * @returns The records.
439
+ */
440
+ readActivity(kind: "accepted" | "duplicate" | "refused" | null, boardId: string | null, beforeSequence: number | null, limit: number, includeAddresses: boolean): Promise<LeaderboardActivityView[]>;
441
+ /**
442
+ * The status view: storage, durability, the definitions problem, boards and fleet-wide per-minute counts (D20, D21).
443
+ * @returns The status.
444
+ */
445
+ status(): Promise<LeaderboardStatusView>;
446
+ /**
447
+ * Records a session join for session-level trust (D10). Fire-and-forget: errors are logged at warn, never thrown.
448
+ * @param event The join or leave (leaves are ignored).
449
+ */
450
+ recordPresence(event: PlayerSessionEvent): void;
451
+ /**
452
+ * The board documents, cached for LEADERBOARD_DEFINITION_CACHE_MS.
453
+ * @returns Board id → document.
454
+ */
455
+ private cachedBoards;
456
+ /**
457
+ * A board for a read, from the cache: public reads see only public boards.
458
+ * @param boardId The board.
459
+ * @param audience "public" or "admin".
460
+ * @returns The board record.
461
+ * @throws LeaderboardError 404 unknownBoard.
462
+ */
463
+ private boardFor;
464
+ /**
465
+ * The rank key of a read: the board, its variant key and the season.
466
+ * @param boardId The board.
467
+ * @param variant The variant.
468
+ * @param seasonId The season, or null for the current one.
469
+ * @param audience "public" checks variant values; "admin" also accepts values a board no longer allows (DR §15).
470
+ * @returns The rank key.
471
+ * @throws LeaderboardError 404 unknownBoard or for an unknown season, 400 variantNotAllowed.
472
+ */
473
+ private rankKeyFor;
474
+ /**
475
+ * A new board record with season 1 starting now.
476
+ * @param definition The valid definition.
477
+ * @returns The record.
478
+ */
479
+ private newBoardRecord;
480
+ /**
481
+ * Imports the definitions file (D11): creates each valid board that does not exist yet and records any problem.
482
+ */
483
+ private importDefinitionsFile;
484
+ /**
485
+ * Moves every anonymous player's live entry, in every kept season of every board, to its ranking's removed list
486
+ * (leaderboard-signed-in-only D4). Entries stay restorable from the console and player records are untouched.
487
+ * Idempotent: a second run finds nothing left to move.
488
+ * @returns How many entries were moved.
489
+ */
490
+ private hideAnonymousEntries;
491
+ /**
492
+ * Moves the anonymous players' live entries of one ranking to its removed list.
493
+ * @param key The ranking.
494
+ * @param nowIso The removal time (ISO).
495
+ * @returns How many entries were moved.
496
+ */
497
+ private hideAnonymousEntriesOf;
498
+ /**
499
+ * Creates a board unless another process or the console already has it.
500
+ * @param definition The valid definition.
501
+ */
502
+ private createBoardIfMissing;
503
+ /**
504
+ * The auth user's player record, created with the claim name (or a default) on first use; an existing record keeps
505
+ * its own name.
506
+ * @param userId The auth user id.
507
+ * @param userDisplayName The name claim, or null.
508
+ * @param userAvatar The avatar claim, or null (stored only when the record is created).
509
+ * @returns The record.
510
+ */
511
+ private userPlayer;
512
+ /**
513
+ * Refreshes an existing user player's name and avatar from a new sign-in (D16); its entries take the new name.
514
+ * @param record The stored player.
515
+ * @param displayName The sign-in's display name (cleaned; a refused name keeps the stored one).
516
+ * @param avatar The sign-in's avatar claim, or null.
517
+ */
518
+ private refreshUserProfile;
519
+ /**
520
+ * The anonymous player a browser's key names, when the key is valid.
521
+ * @param playerKey The anonymous player key, or null.
522
+ * @returns The anonymous record, or null when the key is missing, malformed, unknown, not anonymous or not valid.
523
+ */
524
+ private anonymousPlayerOf;
525
+ /**
526
+ * The player of a server-trust submission: the named player, or one created when unknown and a name is given (DR §6):
527
+ * kind user for a user: id (discord-sign-in F1), else manual.
528
+ * @param request The server submission.
529
+ * @returns The record.
530
+ * @throws LeaderboardError 400 invalidPlayer for an unknown player without a name.
531
+ */
532
+ private serverPlayer;
533
+ /**
534
+ * Cleans a display name with the current rules' blocked words.
535
+ * @param displayName The name (any JSON).
536
+ * @returns The clean name.
537
+ * @throws LeaderboardError 400 nameInvalid or nameBlocked.
538
+ */
539
+ private requireCleanName;
540
+ /**
541
+ * Consumes the per-player and per-address submission limits; a refusal is recorded in activity and thrown.
542
+ * @param context The submission.
543
+ * @throws LeaderboardError 429 rateLimited.
544
+ */
545
+ private consumeSubmissionRates;
546
+ /**
547
+ * Checks and writes one score (DR §10 step 6), recording activity and the metric.
548
+ * @param context The submission.
549
+ * @param submission The score.
550
+ * @returns The score's result.
551
+ */
552
+ private submitScore;
553
+ /**
554
+ * The trust level of one score: server, session when presence passes for its duration (D10), else client.
555
+ * @param context The submission.
556
+ * @param definition The board.
557
+ * @param score The score (a time score must fit between the join and now).
558
+ * @returns The trust level.
559
+ */
560
+ private trustLevelOf;
561
+ /**
562
+ * The incoming entry of a write: submissionCount 1, the service clock's times, the player's current name.
563
+ * @param context The submission.
564
+ * @param score The score.
565
+ * @param metadata The checked metadata.
566
+ * @param trustLevel The trust level.
567
+ * @returns The entry.
568
+ */
569
+ private incomingEntry;
570
+ /**
571
+ * Records and returns an accepted or duplicate score.
572
+ * @param context The submission.
573
+ * @param key The ranking written.
574
+ * @param written The store's result.
575
+ * @param trustLevel The trust level.
576
+ * @returns The result.
577
+ */
578
+ private acceptScore;
579
+ /**
580
+ * Discards a hidden player's score (D18 shadow ban): accepted, outcome kept, no rank, nothing written.
581
+ * @param context The submission.
582
+ * @param key The ranking it would have gone to.
583
+ * @param score The score.
584
+ * @param trustLevel The trust level.
585
+ * @returns The result.
586
+ */
587
+ private discardScore;
588
+ /**
589
+ * Records and returns a refused score.
590
+ * @param context The submission.
591
+ * @param boardId The board named.
592
+ * @param variantKey The variant key, or null when it was not valid.
593
+ * @param reason Why.
594
+ * @returns The result.
595
+ */
596
+ private refuseScore;
597
+ /**
598
+ * Appends one activity record (D21); a failing append is logged at warn and never fails the score.
599
+ * @param context The submission.
600
+ * @param fields The score's fields.
601
+ */
602
+ private appendActivity;
603
+ /**
604
+ * Drops the cached pages of one ranking after a local write.
605
+ * @param key The ranking.
606
+ */
607
+ private forgetCachedReads;
608
+ /**
609
+ * The rank key of an admin moderation call (the board must exist; the season must be kept).
610
+ * @param boardId The board.
611
+ * @param variantKey The variant key.
612
+ * @param seasonId The season.
613
+ * @returns The rank key.
614
+ */
615
+ private adminRankKey;
616
+ /**
617
+ * Writes an admin entry with keep policy latest and no dedupe.
618
+ * @param key The ranking.
619
+ * @param record The board.
620
+ * @param entry The entry.
621
+ * @returns The entry's view with its rank.
622
+ */
623
+ private writeAdminEntry;
624
+ /**
625
+ * Restores a hidden player's entry in one ranking, if it was removed for playerHidden.
626
+ * @param key The ranking.
627
+ * @param playerId The player.
628
+ */
629
+ private restoreHiddenEntry;
630
+ /**
631
+ * Merges one source entry into the target's entry of the same ranking by the board's keep policy.
632
+ * @param key The ranking.
633
+ * @param definition The board.
634
+ * @param sourceEntry The source player's live entry.
635
+ * @param target The target player.
636
+ */
637
+ private mergeEntry;
638
+ /**
639
+ * One entry of a player's detail: live with its rank, or removed with its reason.
640
+ * @param key The ranking.
641
+ * @param playerId The player.
642
+ * @param record The board, or null when it was deleted.
643
+ * @returns The entry view, or null when the player has no entry there.
644
+ */
645
+ private playerEntryView;
646
+ /**
647
+ * Reads a player record.
648
+ * @param playerId The player.
649
+ * @returns The record.
650
+ * @throws LeaderboardError 404 invalidPlayer when it does not exist.
651
+ */
652
+ private requirePlayer;
653
+ /**
654
+ * Creates a manual player (D8) with a cleaned name.
655
+ * @param displayName The name.
656
+ * @returns The record.
657
+ */
658
+ private createManualPlayer;
659
+ /**
660
+ * The board documents read fresh (moderation must not act on a stale cache).
661
+ * @returns Board id → document.
662
+ */
663
+ private freshBoards;
664
+ /**
665
+ * The service clock's time as ISO text.
666
+ * @returns ISO time.
667
+ */
668
+ private nowIso;
669
+ }