@smartico/public-api 0.0.409 → 0.0.410

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 (37) hide show
  1. package/dist/MiniGames/SAWDoAknowledgeRequest.d.ts +2 -0
  2. package/dist/MiniGames/SAWPrize.d.ts +9 -0
  3. package/dist/MiniGames/SAWTemplate.d.ts +1 -0
  4. package/dist/SmarticoAPI.d.ts +1 -1
  5. package/dist/SmarticoLib/index.d.ts +1 -1
  6. package/dist/WSAPI/WSAPIJackpots.d.ts +11 -2
  7. package/dist/WSAPI/WSAPIMiniGames.d.ts +86 -23
  8. package/dist/WSAPI/WSAPITypes.d.ts +12 -12
  9. package/dist/index.js +104 -31
  10. package/dist/index.js.map +1 -1
  11. package/dist/index.modern.mjs +101 -28
  12. package/dist/index.modern.mjs.map +1 -1
  13. package/docs/api/classes/WSAPIJackpots.md +11 -2
  14. package/docs/api/classes/WSAPIMiniGames.md +86 -23
  15. package/docs/api/interfaces/SAWDoAknowledgeRequest.md +8 -0
  16. package/docs/api/interfaces/SAWPrize.md +18 -0
  17. package/docs/api/interfaces/SAWTemplate.md +2 -0
  18. package/docs/api/interfaces/TMiniGamePrize.md +25 -9
  19. package/docs/api/interfaces/TMiniGameTemplate.md +3 -3
  20. package/docs/capabilities/getJackpotEligibleGames.md +11 -2
  21. package/docs/capabilities/getMiniGames.md +35 -12
  22. package/docs/capabilities/miniGameWinAcknowledgeRequest.md +30 -7
  23. package/docs/capabilities/playMiniGame.md +27 -14
  24. package/docs/native/PROTOCOL.md +3 -0
  25. package/docs/ui/jackpots/UIGuide_getJackpotEligibleGames.md +8 -0
  26. package/docs/ui/minigames/UIGuide_getMiniGames.md +24 -0
  27. package/docs/ui/minigames/UIGuide_getMiniGamesHistory.md +1 -1
  28. package/docs/ui/minigames/UIGuide_playMiniGame.md +28 -1
  29. package/package.json +1 -1
  30. package/src/MiniGames/SAWDoAknowledgeRequest.ts +2 -0
  31. package/src/MiniGames/SAWPrize.ts +9 -0
  32. package/src/MiniGames/SAWTemplate.ts +1 -0
  33. package/src/SmarticoAPI.ts +2 -1
  34. package/src/SmarticoLib/index.ts +1 -1
  35. package/src/WSAPI/WSAPIJackpots.ts +11 -2
  36. package/src/WSAPI/WSAPIMiniGames.ts +85 -24
  37. package/src/WSAPI/WSAPITypes.ts +12 -12
@@ -67,14 +67,19 @@ without waiting for the win to be marked delivered. You finalise
67
67
  it later by calling `miniGameWinAcknowledgeRequest` with the
68
68
  `request_id` returned on this result.
69
69
 
70
- What `acknowledge: false` does and does NOT defer:
71
- - For STANDARD prizes the value is credited at spin time
72
- regardless, so opting out does NOT delay the balance change —
73
- it only defers the "delivered" bookkeeping and the `is_claimed`
74
- flag flipping in `getMiniGamesHistory`.
75
- - For operator-configured "explicit claim" prizes the credit IS
76
- deferred until the spin is acknowledged, so those require an
77
- explicit acknowledge to finalise.
70
+ What `acknowledge: false` defers:
71
+ - For STANDARD prizes the value is credited when the spin is
72
+ finalised — by your later acknowledge or, failing that, by the
73
+ server-side fallback below — so opting out delays the balance
74
+ change by at most that fallback window. The `is_claimed` flag in
75
+ `getMiniGamesHistory` flips on the same finalisation.
76
+ - For operator-configured "explicit claim" prizes the credit is
77
+ deferred until your explicit acknowledge — the fallback does not
78
+ cover them.
79
+
80
+ While the spin is un-finalised it can also be finalised as LOST —
81
+ prize discarded back to the pool — via
82
+ `miniGameWinAcknowledgeRequest` with `{ lose: true }`.
78
83
 
79
84
  A server-side fallback auto-acknowledges ordinary un-acknowledged
80
85
  spins after a short delay (about 1–3 minutes), so an ordinary
@@ -105,8 +110,10 @@ refreshed array.
105
110
  time the call resolves. Balance updates flow via the
106
111
  user-properties channel (observe via `getUserProfile`).
107
112
  - Prize value credited per the prize's type (see "Prize handling"
108
- above). Standard prizes are credited at spin time; "explicit
109
- claim" prizes are credited when the spin is acknowledged.
113
+ above) when the spin is finalised — with the default
114
+ auto-acknowledge that happens before the call resolves;
115
+ "explicit claim" prizes are credited only by an explicit
116
+ acknowledge.
110
117
  - The play is recorded server-side for analytics / reporting.
111
118
 
112
119
  **UI guidance**: see [UI Guide — `playMiniGame`](../../docs/ui/minigames/UIGuide_playMiniGame.md).
@@ -153,18 +160,24 @@ if (r.err_code === 0) {
153
160
  ```
154
161
 
155
162
  Manual finalisation (`acknowledge: false`) — e.g. an explicit
156
- "Claim" CTA, or finalising on your own schedule:
163
+ "Claim" CTA, a decline/forfeit flow, or finalising on your own
164
+ schedule:
157
165
  ```ts
158
166
  const r = await window._smartico.api.playMiniGame(game.id, { acknowledge: false });
159
167
  if (r.err_code === 0) {
160
- // Spin resolved but not yet acknowledged. For standard prizes the
161
- // balance already changed server-side; "explicit claim" prizes
162
- // are credited only by the acknowledge below.
168
+ // Spin resolved but not yet finalised — the prize is not credited
169
+ // yet. Your acknowledge below credits it (for standard prizes the
170
+ // server-side fallback would eventually do the same).
163
171
  console.log('[smartico] prize won — show the result / Claim CTA, then finalise');
164
172
 
165
173
  // On the user's Claim click, finalise with the request_id from the result.
166
174
  await window._smartico.api.miniGameWinAcknowledgeRequest(r.request_id);
167
175
  console.log('[smartico] win finalised — refresh getUserProfile / getMiniGames to reflect it');
176
+
177
+ // Or, if the game flow ends in the player declining / losing the
178
+ // drawn prize, finalise the spin as lost instead — the prize is
179
+ // not credited and returns to the prize pool:
180
+ // await window._smartico.api.miniGameWinAcknowledgeRequest(r.request_id, { lose: true });
168
181
  }
169
182
  ```
170
183
 
@@ -1434,6 +1434,8 @@ Each item in `results`:
1434
1434
 
1435
1435
  Acknowledge a mini-game win. Should be called after displaying the win result to the user.
1436
1436
 
1437
+ Optionally finalises the spin as **lost** instead: with `lose: true` the prize is not credited, it is returned to the game's prize pool, and the mini-game "lose" engagement event fires instead of the win one. Only possible while the spin is not yet acknowledged — once the automatic server-side acknowledge fallback has finalised it, `lose: true` is a no-op and the prize stays credited.
1438
+
1437
1439
  #### Request
1438
1440
 
1439
1441
  **ClassId:** `704` (SAW_AKNOWLEDGE_REQUEST)
@@ -1441,6 +1443,7 @@ Acknowledge a mini-game win. Should be called after displaying the win result to
1441
1443
  | Field | Type | Description |
1442
1444
  |-------|------|-------------|
1443
1445
  | `request_id` | `string` | Request ID from the spin response |
1446
+ | `lose` | `boolean` | Optional. `true` finalises the spin as lost: prize not credited, returned to the prize pool. Omit or `false` to deliver the win |
1444
1447
 
1445
1448
  #### Response
1446
1449
 
@@ -61,6 +61,14 @@ manually if needed.
61
61
  - For long sessions, re-call when reopening the tab past the 30 s
62
62
  window.
63
63
 
64
+ ## Visitor mode
65
+
66
+ Supported via `_smartico.vapi(lang).getJackpotEligibleGames(...)`. The
67
+ eligible-games list is template-level (which games contribute to the
68
+ pot) and carries no per-user fields, so a visitor session sees the same
69
+ list an identified user would. The `lang` passed to `_smartico.vapi(lang)`
70
+ drives the translation of game names.
71
+
64
72
  ## Mobile vs desktop
65
73
 
66
74
  - **Mobile**: 2- or 3-column tile grid.
@@ -99,6 +99,30 @@ error.
99
99
  | `promo_image` | ~2:1 wide, 500×240 px | Featured / hero artwork |
100
100
  | `prizes[].icon` | 1:1 (square) | Per-prize icon |
101
101
 
102
+ ## Prize stock / scarcity UI (`expose_game_stat_on_api`)
103
+
104
+ When the operator enables "expose game statistics" on a template
105
+ (`template.expose_game_stat_on_api === true`), each prize carries
106
+ live stock statistics you can build scarcity affordances from:
107
+
108
+ - `pool` — remaining stock → "Only 3 left!" badges; pair with
109
+ `pool_initial` for a depletion bar (`pool / pool_initial`).
110
+ - `wins_count` — total wins across all players → social proof
111
+ ("won 120 times").
112
+ - `weekdays` (ISO 1–7) and `active_from_ts` / `active_till_ts` —
113
+ the prize's availability schedule → grey out prizes not winnable
114
+ today, or show "available Mon–Fri" hints. Evaluate against
115
+ `relative_period_timezone` (minutes, JS `getTimezoneOffset`
116
+ convention), not the device timezone.
117
+
118
+ The values refresh after every play, so re-render stock badges
119
+ from the `onUpdate` callback. When the setting is disabled (the
120
+ default) these fields are absent — build the prize strip from the
121
+ definition fields only and don't reserve empty space for stock
122
+ badges. Exception: `pool` is always present for MatchX / Quiz
123
+ templates. A prize with `is_surcharge: true` never runs out —
124
+ skip stock badges for it.
125
+
102
126
  ## Status-specific visual treatments
103
127
 
104
128
  - **Playable**: full-color card; Play CTA enabled.
@@ -24,7 +24,7 @@ Fields rendered per row:
24
24
  | Field | Source | Notes |
25
25
  |---|---|---|
26
26
  | Template icon | `template.thumbnail` (or similar) | 1:1 |
27
- | Prize name | Look up `template.prizes[i]` by `saw_prize_id` | Display the prize's `name`. |
27
+ | Prize name | Look up `template.prizes[i]` by `saw_prize_id` | Display the prize's `name`. A spin finalised as lost (`miniGameWinAcknowledgeRequest` with `lose: true`) has no prize attached — render it as a loss. |
28
28
  | Prize amount | `template.prizes[i].prize_value` or `prize_amount` | E.g. "100 points" |
29
29
  | Spin date | `create_date_ts` | Format as user-local relative time ("2h ago") or short date |
30
30
  | Claim status | `is_claimed` | Show check-mark when true; "Pending claim" CTA when false |
@@ -91,7 +91,9 @@ with the `request_id` from that play result when the user taps Claim.
91
91
  [`getMiniGamesHistory`](../../api/classes/WSAPIMiniGames.md#getminigameshistory)
92
92
  row if you need to recover it later.) Note: "explicit claim" prizes
93
93
  are NOT covered by the server-side auto-acknowledge fallback, so for
94
- these you MUST acknowledge or the prize is never credited.
94
+ these you MUST acknowledge or the prize is never credited. To let
95
+ the user decline the prize instead of claiming it, see "Decline /
96
+ forfeit" below.
95
97
 
96
98
  Modal contents per prize:
97
99
 
@@ -105,6 +107,31 @@ Modal contents per prize:
105
107
  - Optional additional CTA: `prize.acknowledge_action_title_additional`
106
108
  + `prize.acknowledge_dp_additional`
107
109
 
110
+ ## Decline / forfeit ("lose") flows
111
+
112
+ Some game mechanics let the player decline or forfeit the drawn
113
+ prize — a gamble/discard step, a "keep it or risk it" offer, or a
114
+ game where the player's final action decides whether the pre-drawn
115
+ prize is actually won. Implement these with manual finalisation:
116
+
117
+ 1. Play with `acknowledge: false` so the SDK does not auto-finalise.
118
+ 2. Run the game / choice UI.
119
+ 3. Finalise per the outcome:
120
+ - Keep / win →
121
+ `miniGameWinAcknowledgeRequest(request_id)` — prize credited.
122
+ - Decline / lose →
123
+ `miniGameWinAcknowledgeRequest(request_id, { lose: true })` —
124
+ prize NOT credited, returned to the prize pool for other
125
+ players. Show the same "Better luck next time" treatment as a
126
+ `no-prize` slot (below).
127
+
128
+ Timing: standard prizes are auto-finalised as WON by the
129
+ server-side fallback after ~1–3 minutes, so send the lose decision
130
+ promptly — after the fallback fires, `lose: true` is a no-op and
131
+ the prize stays credited. "Explicit claim" prizes are exempt from
132
+ the fallback, so those have no time pressure. Once a spin is
133
+ finalised either way, further acknowledge calls are no-ops.
134
+
108
135
  ## "No prize" handling
109
136
 
110
137
  When the won prize has `prize_type === 'no-prize'`, the user has
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@smartico/public-api",
3
- "version": "0.0.409",
3
+ "version": "0.0.410",
4
4
  "description": "Smartico public API",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",
@@ -2,4 +2,6 @@ import { ProtocolMessage } from '.././Base/ProtocolMessage';
2
2
 
3
3
  export interface SAWDoAknowledgeRequest extends ProtocolMessage {
4
4
  request_id: string; // guid
5
+ /** When true, finalises the spin as lost: the prize is not credited and is returned to the prize pool. */
6
+ lose?: boolean;
5
7
  }
@@ -10,14 +10,23 @@ export interface SAWPrize {
10
10
  place_from?: number;
11
11
  place_to?: number;
12
12
  sawUniqueWinId?: string;
13
+ /** Remaining stock. Present only when the template's `expose_game_stat_on_api` is enabled; always present for MatchX / Quiz games */
13
14
  pool?: number;
15
+ /** Initial (configured) stock. Present regardless of `expose_game_stat_on_api` */
14
16
  pool_initial?: number;
17
+ /** Times the prize has been won, across all players. Present only when `expose_game_stat_on_api` is enabled */
15
18
  wins_count?: number;
19
+ /** ISO weekday numbers (1 = Monday … 7 = Sunday) the prize can be won on; absent = any day. Present only when `expose_game_stat_on_api` is enabled */
16
20
  weekdays?: number[];
21
+ /** Prize availability window start (epoch ms), evaluated against `relative_period_timezone`. Present only when `expose_game_stat_on_api` is enabled */
17
22
  active_from_ts?: number;
23
+ /** Prize availability window end (epoch ms), evaluated against `relative_period_timezone`. Present only when `expose_game_stat_on_api` is enabled */
18
24
  active_till_ts?: number;
25
+ /** Timezone offset in minutes for `weekdays` / active-window evaluation (UTC minus local, as in JS `Date.getTimezoneOffset()`) */
19
26
  relative_period_timezone?: number;
27
+ /** When true, the prize stays winnable at `pool` 0 (unlimited stock) */
20
28
  is_surcharge?: boolean;
29
+ /** Always `false` in API responses — deleted prizes are excluded server-side */
21
30
  is_deleted?: boolean;
22
31
  prize_details_json?: {[key: string]: any};
23
32
  max_give_period_type_id?: AttemptPeriodType;
@@ -44,6 +44,7 @@ export interface SAWTemplate {
44
44
  lottie_animation_speed?: number;
45
45
  };
46
46
 
47
+ /** Operator template setting. When enabled, the per-prize stock statistics (`pool`, `wins_count`, `weekdays`, `active_from_ts` / `active_till_ts`) are populated on `prizes`; when disabled (default) the server strips them from the response (`pool` is kept for MatchX / Quiz games). */
47
48
  expose_game_stat_on_api?: boolean;
48
49
 
49
50
  // AA: releavnt only in the context of the SAWPrizeDropWinPush
@@ -680,12 +680,13 @@ class SmarticoAPI {
680
680
  return SAWTemplatesTransform((await this.sawGetTemplates(user_ext_id)).templates);
681
681
  }
682
682
 
683
- public async doAcknowledgeRequest(user_ext_id: string, request_id: string): Promise<SAWDoAknowledgeResponse> {
683
+ public async doAcknowledgeRequest(user_ext_id: string, request_id: string, lose?: boolean): Promise<SAWDoAknowledgeResponse> {
684
684
  const message = this.buildMessage<SAWDoAknowledgeRequest, SAWDoAknowledgeResponse>(
685
685
  user_ext_id,
686
686
  ClassId.SAW_AKNOWLEDGE_REQUEST,
687
687
  {
688
688
  request_id,
689
+ lose,
689
690
  },
690
691
  );
691
692
 
@@ -2021,7 +2021,7 @@ declare class SmarticoAPI {
2021
2021
  coreCheckSegments(user_ext_id: string, segment_id: number[]): Promise<TSegmentCheckResult[]>;
2022
2022
  sawGetTemplates(user_ext_id: string, lang?: string, is_visitor_mode?: boolean): Promise<SAWGetTemplatesResponse>;
2023
2023
  sawGetTemplatesT(user_ext_id: string): Promise<TMiniGameTemplate[]>;
2024
- doAcknowledgeRequest(user_ext_id: string, request_id: string): Promise<SAWDoAknowledgeResponse>;
2024
+ doAcknowledgeRequest(user_ext_id: string, request_id: string, lose?: boolean): Promise<SAWDoAknowledgeResponse>;
2025
2025
  sawSpinRequest(user_ext_id: string, saw_template_id: number, round_id?: number): Promise<SAWDoSpinResponse>;
2026
2026
  missionOptIn(user_ext_id: string, mission_id: number): Promise<AchievementOptinResponse>;
2027
2027
  missionClaimPrize(user_ext_id: string, mission_id: number, ach_completed_id: number): Promise<AchClaimPrizeResponse>;
@@ -396,7 +396,7 @@ export class WSAPIJackpots extends WSAPIClans {
396
396
  *
397
397
  * @remarks
398
398
  * **Preconditions**
399
- * - User must be authenticated. Visitor mode not supported.
399
+ * - No authentication required — works in both identified and visitor mode.
400
400
  * - `jp_template_id` is mandatory.
401
401
  *
402
402
  * **`onUpdate` caveat**
@@ -414,7 +414,12 @@ export class WSAPIJackpots extends WSAPIClans {
414
414
  * Non-zero `errCode` on control-group users or generic server errors.
415
415
  * Branch on `errCode === 0` and surface `errMsg` on failure.
416
416
  *
417
- * **Visitor mode**: not supported.
417
+ * **Visitor mode**: supported via
418
+ * `_smartico.vapi(lang).getJackpotEligibleGames(...)`. The eligible-games
419
+ * list is template-level (which games contribute to the pot) and carries no
420
+ * per-user fields, so a visitor session receives the same list an identified
421
+ * user would. The `lang` passed to `_smartico.vapi(lang)` drives the
422
+ * translation of game names.
418
423
  *
419
424
  * **UI guidance**: see [UI Guide — `getJackpotEligibleGames`](../../docs/ui/jackpots/UIGuide_getJackpotEligibleGames.md).
420
425
  *
@@ -432,6 +437,10 @@ export class WSAPIJackpots extends WSAPIClans {
432
437
  *
433
438
  * const r = await window._smartico.api.getJackpotEligibleGames({ jp_template_id: 42 });
434
439
  * console.log('[smartico] render', r.eligible_games.length, 'eligible game tiles');
440
+ *
441
+ * // Visitor mode — same shape, language driven by the vapi(lang) argument
442
+ * const visitor = await window._smartico.vapi('EN').getJackpotEligibleGames({ jp_template_id: 42 });
443
+ * console.log('[smartico] visitor eligible games:', visitor.eligible_games.length);
435
444
  * ```
436
445
  */
437
446
  public async getJackpotEligibleGames({ jp_template_id, onUpdate } : {
@@ -64,6 +64,27 @@ export class WSAPIMiniGames extends WSAPIRaffles {
64
64
  * games server (not this SDK); the SAW spin is fired
65
65
  * server-internally to deduct the buy-in.
66
66
  *
67
+ * **Per-prize statistics (`expose_game_stat_on_api`)**
68
+ * Each template's `prizes` array always carries the definition
69
+ * fields — name, icon, `prize_type`, `prize_value`, acknowledge
70
+ * configuration. The stock-statistics fields are gated by an
71
+ * operator template setting, surfaced as
72
+ * `expose_game_stat_on_api`:
73
+ * - Populated when enabled: `pool` (remaining stock),
74
+ * `wins_count` (total wins across all players), `weekdays`
75
+ * (ISO 1–7 days the prize can be won), `active_from_ts` /
76
+ * `active_till_ts` (prize availability window).
77
+ * - Omitted when disabled (the default) — this keeps the live
78
+ * prize economy (stock levels, win rates, schedules) hidden
79
+ * from players.
80
+ * - Exception: `pool` is always populated for `MatchX` / `Quiz`
81
+ * templates, whose game flow needs the remaining stock.
82
+ * - `pool_initial` is populated regardless of the setting.
83
+ * When enabled, the values are also kept current — the server
84
+ * refreshes the prize rows on each fetch and drops its template
85
+ * caches after every play, so `pool` / `wins_count` are safe to
86
+ * drive an "X prizes left" scarcity UI.
87
+ *
67
88
  * **Cache TTL**: the SDK caches the response for 30 seconds. Cache
68
89
  * is fully cleared on login / logout.
69
90
  *
@@ -290,14 +311,19 @@ export class WSAPIMiniGames extends WSAPIRaffles {
290
311
  * it later by calling {@link miniGameWinAcknowledgeRequest} with the
291
312
  * `request_id` returned on this result.
292
313
  *
293
- * What `acknowledge: false` does and does NOT defer:
294
- * - For STANDARD prizes the value is credited at spin time
295
- * regardless, so opting out does NOT delay the balance change —
296
- * it only defers the "delivered" bookkeeping and the `is_claimed`
297
- * flag flipping in {@link getMiniGamesHistory}.
298
- * - For operator-configured "explicit claim" prizes the credit IS
299
- * deferred until the spin is acknowledged, so those require an
300
- * explicit acknowledge to finalise.
314
+ * What `acknowledge: false` defers:
315
+ * - For STANDARD prizes the value is credited when the spin is
316
+ * finalised — by your later acknowledge or, failing that, by the
317
+ * server-side fallback below — so opting out delays the balance
318
+ * change by at most that fallback window. The `is_claimed` flag in
319
+ * {@link getMiniGamesHistory} flips on the same finalisation.
320
+ * - For operator-configured "explicit claim" prizes the credit is
321
+ * deferred until your explicit acknowledge — the fallback does not
322
+ * cover them.
323
+ *
324
+ * While the spin is un-finalised it can also be finalised as LOST —
325
+ * prize discarded back to the pool — via
326
+ * {@link miniGameWinAcknowledgeRequest} with `{ lose: true }`.
301
327
  *
302
328
  * A server-side fallback auto-acknowledges ordinary un-acknowledged
303
329
  * spins after a short delay (about 1–3 minutes), so an ordinary
@@ -328,8 +354,10 @@ export class WSAPIMiniGames extends WSAPIRaffles {
328
354
  * time the call resolves. Balance updates flow via the
329
355
  * user-properties channel (observe via {@link getUserProfile}).
330
356
  * - Prize value credited per the prize's type (see "Prize handling"
331
- * above). Standard prizes are credited at spin time; "explicit
332
- * claim" prizes are credited when the spin is acknowledged.
357
+ * above) when the spin is finalised — with the default
358
+ * auto-acknowledge that happens before the call resolves;
359
+ * "explicit claim" prizes are credited only by an explicit
360
+ * acknowledge.
333
361
  * - The play is recorded server-side for analytics / reporting.
334
362
  *
335
363
  * **UI guidance**: see [UI Guide — `playMiniGame`](../../docs/ui/minigames/UIGuide_playMiniGame.md).
@@ -394,18 +422,24 @@ export class WSAPIMiniGames extends WSAPIRaffles {
394
422
  *
395
423
  * @example
396
424
  * Manual finalisation (`acknowledge: false`) — e.g. an explicit
397
- * "Claim" CTA, or finalising on your own schedule:
425
+ * "Claim" CTA, a decline/forfeit flow, or finalising on your own
426
+ * schedule:
398
427
  * ```ts
399
428
  * const r = await window._smartico.api.playMiniGame(game.id, { acknowledge: false });
400
429
  * if (r.err_code === 0) {
401
- * // Spin resolved but not yet acknowledged. For standard prizes the
402
- * // balance already changed server-side; "explicit claim" prizes
403
- * // are credited only by the acknowledge below.
430
+ * // Spin resolved but not yet finalised — the prize is not credited
431
+ * // yet. Your acknowledge below credits it (for standard prizes the
432
+ * // server-side fallback would eventually do the same).
404
433
  * console.log('[smartico] prize won — show the result / Claim CTA, then finalise');
405
434
  *
406
435
  * // On the user's Claim click, finalise with the request_id from the result.
407
436
  * await window._smartico.api.miniGameWinAcknowledgeRequest(r.request_id);
408
437
  * console.log('[smartico] win finalised — refresh getUserProfile / getMiniGames to reflect it');
438
+ *
439
+ * // Or, if the game flow ends in the player declining / losing the
440
+ * // drawn prize, finalise the spin as lost instead — the prize is
441
+ * // not credited and returns to the prize pool:
442
+ * // await window._smartico.api.miniGameWinAcknowledgeRequest(r.request_id, { lose: true });
409
443
  * }
410
444
  * ```
411
445
  */
@@ -433,9 +467,10 @@ export class WSAPIMiniGames extends WSAPIRaffles {
433
467
 
434
468
  /**
435
469
  * Manually acknowledges a mini-game spin — marks the win delivered
436
- * server-side. Most consumers do NOT need this: {@link playMiniGame}
437
- * acknowledges by default (`acknowledge: true`) and
438
- * {@link playMiniGameBatch} acknowledges automatically. Call this
470
+ * server-side, or (with `lose: true`) finalises it as lost and
471
+ * returns the prize to the pool. Most consumers do NOT need this:
472
+ * {@link playMiniGame} acknowledges by default (`acknowledge: true`)
473
+ * and {@link playMiniGameBatch} acknowledges automatically. Call this
439
474
  * directly only when you took ownership of the acknowledge step or
440
475
  * need to recover a lost one.
441
476
  *
@@ -458,6 +493,23 @@ export class WSAPIMiniGames extends WSAPIRaffles {
458
493
  * `client_request_id` on a {@link getMiniGamesHistory} row are the
459
494
  * same correlation id — this method accepts either.
460
495
  *
496
+ * **Finalising as lost (`lose: true`)**
497
+ * Pass `{ lose: true }` to finalise the spin as LOST instead of won:
498
+ * the prize is NOT credited and is returned to the game's prize pool
499
+ * (available again for other players), and the spin fires the
500
+ * mini-game "lose" engagement event instead of the win one. On the
501
+ * next {@link getMiniGamesHistory} fetch the row shows `is_claimed:
502
+ * true` with no prize attached. Use this for game mechanics where the
503
+ * player can decline or forfeit the drawn prize — e.g. a
504
+ * gamble/discard step, or a client-driven game where the user's final
505
+ * action decides whether the pre-drawn prize is actually won. It only
506
+ * works on a spin that is not yet finalised, so it requires playing
507
+ * with `acknowledge: false` and calling promptly — once the automatic
508
+ * acknowledge or the server-side fallback (below) has finalised the
509
+ * spin, `lose: true` is a no-op and the prize stays credited.
510
+ * ("Explicit claim" prizes are exempt from the fallback, so for them
511
+ * there is no time pressure.)
512
+ *
461
513
  * **Idempotency**: safe. Acknowledging a spin that is already
462
514
  * finalised — by you, by the automatic acknowledge, or by the
463
515
  * fallback — is a no-op with no double credit. Acknowledging a
@@ -472,11 +524,12 @@ export class WSAPIMiniGames extends WSAPIRaffles {
472
524
  * call here.
473
525
  *
474
526
  * **Side effects** (first successful call for an un-acknowledged spin)
475
- * - For "explicit claim" prizes, the prize value is credited on this
476
- * call. For standard prizes the value was already credited at spin
477
- * time (see {@link playMiniGame} "Prize handling"); this call only
478
- * marks the win delivered.
479
- * - The spin's `is_claimed` flips to `true` on the next
527
+ * - Default (win): the prize value is credited on this call — this is
528
+ * the finalisation step that credits standard and "explicit claim"
529
+ * prizes alike (see {@link playMiniGame} "Prize handling").
530
+ * - With `lose: true`: no credit; the prize returns to the prize pool
531
+ * and the "lose" engagement event fires.
532
+ * - Either way the spin's `is_claimed` flips to `true` on the next
480
533
  * {@link getMiniGamesHistory} fetch.
481
534
  *
482
535
  * **Visitor mode**: not supported.
@@ -486,6 +539,10 @@ export class WSAPIMiniGames extends WSAPIRaffles {
486
539
  * (played with `acknowledge: false`), or the
487
540
  * `client_request_id` of a
488
541
  * {@link getMiniGamesHistory} row.
542
+ * @param options.lose Optional. When `true`, finalises the spin as
543
+ * lost — the prize is not credited and returns
544
+ * to the prize pool (see "Finalising as lost").
545
+ * Omit (or pass `false`) to deliver the win.
489
546
  *
490
547
  * @example
491
548
  * ```ts
@@ -496,6 +553,10 @@ export class WSAPIMiniGames extends WSAPIRaffles {
496
553
  * await window._smartico.api.miniGameWinAcknowledgeRequest(r.request_id);
497
554
  * }
498
555
  *
556
+ * // Decline / forfeit — finalise the same spin as lost instead:
557
+ * // the prize is not credited and goes back to the prize pool.
558
+ * await window._smartico.api.miniGameWinAcknowledgeRequest(r.request_id, { lose: true });
559
+ *
499
560
  * // Recovery — re-acknowledge any spins a batch acknowledge missed.
500
561
  * const history = await window._smartico.api.getMiniGamesHistory({ limit: 20 });
501
562
  * for (const row of history.filter(h => !h.is_claimed)) {
@@ -504,8 +565,8 @@ export class WSAPIMiniGames extends WSAPIRaffles {
504
565
  * }
505
566
  * ```
506
567
  */
507
- public async miniGameWinAcknowledgeRequest(request_id: string) {
508
- return this.api.doAcknowledgeRequest(this.userExtId, request_id);
568
+ public async miniGameWinAcknowledgeRequest(request_id: string, { lose }: { lose?: boolean } = {}) {
569
+ return this.api.doAcknowledgeRequest(this.userExtId, request_id, lose);
509
570
  }
510
571
 
511
572
  /**
@@ -59,23 +59,23 @@ export interface TMiniGamePrize {
59
59
  second_btn_action_title?: string;
60
60
  /** Message when the prize pool is empty for that specific prize */
61
61
  out_of_stock_message?: string;
62
- /** Number of items in stock */
62
+ /** Remaining stock of the prize — decrements on each win, refunded if the spin is finalised as lost. Populated only when the template's `expose_game_stat_on_api` is enabled; always populated for MatchX / Quiz games */
63
63
  pool?: number;
64
- /** Initial number of items in stock */
64
+ /** Initial (configured) stock of the prize. Populated regardless of `expose_game_stat_on_api` */
65
65
  pool_initial?: number;
66
- /** Number of wins in game */
66
+ /** Number of times the prize has been won, across all players. Populated only when the template's `expose_game_stat_on_api` is enabled */
67
67
  wins_count?: number;
68
- /** Number of days of week, when the prize can be available */
68
+ /** ISO weekday numbers (1 = Monday … 7 = Sunday) on which the prize can be won; absent = any day. Populated only when the template's `expose_game_stat_on_api` is enabled */
69
69
  weekdays?: number[];
70
- /** Holds time from which prize will become available, for the prizes that are targeted to be available from specific time (UNIX timestamp) */
70
+ /** Time from which the prize can be won (epoch ms), evaluated against `relative_period_timezone`. Populated only when the template's `expose_game_stat_on_api` is enabled */
71
71
  active_from_ts?: number;
72
- /** Holds time till which prize will become available, for the prizes that are targeted to be available from specific time (UNIX timestamp) */
72
+ /** Time until which the prize can be won (epoch ms), evaluated against `relative_period_timezone`. Populated only when the template's `expose_game_stat_on_api` is enabled */
73
73
  active_till_ts?: number;
74
- /** Time zone to ensure each day aligns with your local midnight. */
74
+ /** Timezone offset in minutes used to evaluate `weekdays` and the active window (UTC minus local, as in JS `Date.getTimezoneOffset()` — e.g. `-180` for UTC+3) */
75
75
  relative_period_timezone?: number;
76
- /** Flag indicating that the prize is surcharged (available all the time, despite pool numbers) */
76
+ /** When true, the prize stays winnable even when its `pool` reaches 0 (effectively unlimited stock) */
77
77
  is_surcharge?: boolean;
78
- /** Flag indicating the state of the prize */
78
+ /** Always `false` in API responses — deleted prizes are excluded server-side */
79
79
  is_deleted?: boolean;
80
80
  /** The custom data of the mini-game defined by operator in the BackOffice. Can be a JSON object, string or number */
81
81
  custom_data?: any;
@@ -208,7 +208,7 @@ export interface TMiniGameTemplate {
208
208
  /** List of prizes for mini-games */
209
209
  prizes: TMiniGamePrize[];
210
210
 
211
- /** When enabled, the number of items in the pool and number of won items will be exposed in the Retention API and in the UI Widgets */
211
+ /** Operator template setting. When enabled, the per-prize stock statistics (`pool`, `wins_count`, `weekdays`, `active_from_ts` / `active_till_ts`) are populated on `prizes` and kept current after every play; when disabled (default) those fields are omitted. See `getMiniGames` "Per-prize statistics" */
212
212
  expose_game_stat_on_api?: boolean;
213
213
 
214
214
  /** Time zone to ensure each day aligns with your local midnight. */
@@ -219,7 +219,7 @@ export interface TMiniGameTemplate {
219
219
  activeTillDate?: number;
220
220
  /** The amount of steps to complete the game and gather the prize */
221
221
  steps_to_finish_game?: number;
222
- /** Hold the id of the custom section */
222
+ /** ID of the operator-defined custom section (widget menu grouping) the mini-game is assigned to */
223
223
  custom_section_id?: number;
224
224
 
225
225
  /** The UI definition of the mini-game */
@@ -232,7 +232,7 @@ export interface TMiniGameTemplate {
232
232
  max_number_of_attempts?: number;
233
233
  /** The period of time in milliseconds during which the user can do the maximum number of attempts */
234
234
  max_spins_period_ms?: number;
235
- /** The ID of the user spin id to expose on the game */
235
+ /** Which identifier to show next to a win result for transparency/audit — 'userId' (the player's external user id) or 'spinId' (the spin's transaction id). Absent when the operator disabled it */
236
236
  expose_user_spin_id?: SAWExposeUserSpinIdName;
237
237
  }
238
238