@smartico/public-api 0.0.402 → 0.0.404

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 (153) hide show
  1. package/.claude/skills/api-tsdoc/SKILL.md +675 -0
  2. package/.claude/skills/api-tsdoc-final/SKILL.md +266 -0
  3. package/.claude/skills/api-tsdoc-howto/SKILL.md +143 -0
  4. package/dist/MiniGames/SAWTemplate.d.ts +4 -0
  5. package/dist/NodeCache.d.ts +1 -0
  6. package/dist/OCache.d.ts +7 -0
  7. package/dist/SmarticoGlobal.d.ts +0 -6
  8. package/dist/WSAPI/WSAPITypes.d.ts +43 -0
  9. package/dist/WSAPI/WSAPIUser.d.ts +3 -0
  10. package/dist/index.js +92 -33
  11. package/dist/index.js.map +1 -1
  12. package/dist/index.modern.mjs +60 -10
  13. package/dist/index.modern.mjs.map +1 -1
  14. package/docs/api/interfaces/TUserProfile.md +136 -0
  15. package/docs/capabilities/_responses/buyStoreItem.json +4 -0
  16. package/docs/capabilities/_responses/claimBonus.json +4 -0
  17. package/docs/capabilities/_responses/gamePickGetActiveRound.json +95 -0
  18. package/docs/capabilities/_responses/gamePickGetActiveRounds.json +191 -0
  19. package/docs/capabilities/_responses/gamePickGetBoard.json +47 -0
  20. package/docs/capabilities/_responses/gamePickGetGameInfo.json +355 -0
  21. package/docs/capabilities/_responses/gamePickGetHistory.json +191 -0
  22. package/docs/capabilities/_responses/gamePickGetUserInfo.json +14 -0
  23. package/docs/capabilities/_responses/getAchCategories.json +12 -0
  24. package/docs/capabilities/_responses/getActivityLog.json +1 -0
  25. package/docs/capabilities/_responses/getAvatarPrompts.json +16 -0
  26. package/docs/capabilities/_responses/getAvatarsCustomized.json +12 -0
  27. package/docs/capabilities/_responses/getAvatarsList.json +24 -0
  28. package/docs/capabilities/_responses/getBadges.json +98 -0
  29. package/docs/capabilities/_responses/getBonuses.json +18 -0
  30. package/docs/capabilities/_responses/getClanInfo.json +39 -0
  31. package/docs/capabilities/_responses/getClans.json +35 -0
  32. package/docs/capabilities/_responses/getCurrentLevel.json +20 -0
  33. package/docs/capabilities/_responses/getCustomSections.json +25 -0
  34. package/docs/capabilities/_responses/getInboxMessageBody.json +7 -0
  35. package/docs/capabilities/_responses/getInboxMessages.json +18 -0
  36. package/docs/capabilities/_responses/getInboxUnreadCount.json +1 -0
  37. package/docs/capabilities/_responses/getJackpotEligibleGames.json +20 -0
  38. package/docs/capabilities/_responses/getJackpotWinners.json +28 -0
  39. package/docs/capabilities/_responses/getLeaderBoard.json +45 -0
  40. package/docs/capabilities/_responses/getLevels.json +40 -0
  41. package/docs/capabilities/_responses/getMiniGames.json +208 -0
  42. package/docs/capabilities/_responses/getMiniGamesHistory.json +1 -0
  43. package/docs/capabilities/_responses/getMissions.json +117 -0
  44. package/docs/capabilities/_responses/getRaffleDrawRun.json +62 -0
  45. package/docs/capabilities/_responses/getRaffleDrawRunsHistory.json +34 -0
  46. package/docs/capabilities/_responses/getRaffles.json +140 -0
  47. package/docs/capabilities/_responses/getStoreCategories.json +12 -0
  48. package/docs/capabilities/_responses/getStoreItems.json +47 -0
  49. package/docs/capabilities/_responses/getStorePurchasedItems.json +49 -0
  50. package/docs/capabilities/_responses/getTournamentInstanceInfo.json +75 -0
  51. package/docs/capabilities/_responses/getTournamentsList.json +66 -0
  52. package/docs/capabilities/_responses/getTranslations.json +25 -0
  53. package/docs/capabilities/_responses/getUserLevelExtraCounters.json +4 -0
  54. package/docs/capabilities/_responses/getUserProfile.json +34 -0
  55. package/docs/capabilities/_responses/jackpotGet.json +113 -0
  56. package/docs/capabilities/_responses/jackpotOptIn.json +9 -0
  57. package/docs/capabilities/_responses/jackpotOptOut.json +9 -0
  58. package/docs/capabilities/_responses/markAllInboxMessagesAsRead.json +4 -0
  59. package/docs/capabilities/_responses/markInboxMessageAsRead.json +4 -0
  60. package/docs/capabilities/_responses/markUnmarkInboxMessageAsFavorite.json +4 -0
  61. package/docs/capabilities/_responses/miniGameWinAcknowledgeRequest.json +10 -0
  62. package/docs/capabilities/_responses/playMiniGame.json +6 -0
  63. package/docs/capabilities/_responses/playMiniGameBatch.json +9 -0
  64. package/docs/capabilities/_responses/registerInTournament.json +4 -0
  65. package/docs/capabilities/_responses/requestMissionOptIn.json +4 -0
  66. package/docs/capabilities/_responses/setAvatar.json +4 -0
  67. package/docs/capabilities/avatarsCustomize.md +115 -0
  68. package/docs/capabilities/buyStoreItem.md +179 -0
  69. package/docs/capabilities/checkSegmentListMatch.md +69 -0
  70. package/docs/capabilities/checkSegmentMatch.md +74 -0
  71. package/docs/capabilities/claimBonus.md +125 -0
  72. package/docs/capabilities/claimRafflePrize.md +116 -0
  73. package/docs/capabilities/deleteAllInboxMessages.md +66 -0
  74. package/docs/capabilities/deleteInboxMessage.md +60 -0
  75. package/docs/capabilities/gamePickGetActiveRound.md +248 -0
  76. package/docs/capabilities/gamePickGetActiveRounds.md +259 -0
  77. package/docs/capabilities/gamePickGetBoard.md +202 -0
  78. package/docs/capabilities/gamePickGetGameInfo.md +318 -0
  79. package/docs/capabilities/gamePickGetHistory.md +244 -0
  80. package/docs/capabilities/gamePickGetRoundInfoForUser.md +189 -0
  81. package/docs/capabilities/gamePickGetUserInfo.md +91 -0
  82. package/docs/capabilities/gamePickSubmitSelection.md +222 -0
  83. package/docs/capabilities/gamePickSubmitSelectionQuiz.md +198 -0
  84. package/docs/capabilities/getAchCategories.md +119 -0
  85. package/docs/capabilities/getActivityLog.md +108 -0
  86. package/docs/capabilities/getAvatarPrompts.md +81 -0
  87. package/docs/capabilities/getAvatarsCustomized.md +96 -0
  88. package/docs/capabilities/getAvatarsList.md +101 -0
  89. package/docs/capabilities/getBadges.md +237 -0
  90. package/docs/capabilities/getBonuses.md +159 -0
  91. package/docs/capabilities/getClanInfo.md +164 -0
  92. package/docs/capabilities/getClanTournamentPlayers.md +112 -0
  93. package/docs/capabilities/getClans.md +168 -0
  94. package/docs/capabilities/getCurrentLevel.md +123 -0
  95. package/docs/capabilities/getCustomSections.md +96 -0
  96. package/docs/capabilities/getInboxMessageBody.md +87 -0
  97. package/docs/capabilities/getInboxMessages.md +146 -0
  98. package/docs/capabilities/getInboxUnreadCount.md +54 -0
  99. package/docs/capabilities/getJackpotEligibleGames.md +93 -0
  100. package/docs/capabilities/getJackpotWinners.md +113 -0
  101. package/docs/capabilities/getLeaderBoard.md +187 -0
  102. package/docs/capabilities/getLeaderBoards.md +88 -0
  103. package/docs/capabilities/getLevels.md +118 -0
  104. package/docs/capabilities/getMiniGames.md +295 -0
  105. package/docs/capabilities/getMiniGamesHistory.md +183 -0
  106. package/docs/capabilities/getMissions.md +253 -0
  107. package/docs/capabilities/getRaffleDrawRun.md +210 -0
  108. package/docs/capabilities/getRaffleDrawRunsHistory.md +116 -0
  109. package/docs/capabilities/getRaffleWonPrizes.md +153 -0
  110. package/docs/capabilities/getRaffles.md +249 -0
  111. package/docs/capabilities/getRelatedItemsForGame.md +236 -0
  112. package/docs/capabilities/getStoreCategories.md +128 -0
  113. package/docs/capabilities/getStoreItems.md +260 -0
  114. package/docs/capabilities/getStorePurchasedItems.md +280 -0
  115. package/docs/capabilities/getTournamentInstanceInfo.md +301 -0
  116. package/docs/capabilities/getTournamentsList.md +234 -0
  117. package/docs/capabilities/getTranslations.md +95 -0
  118. package/docs/capabilities/getUserLevelExtraCounters.md +92 -0
  119. package/docs/capabilities/getUserProfile.md +184 -0
  120. package/docs/capabilities/jackpotGet.md +173 -0
  121. package/docs/capabilities/jackpotOptIn.md +94 -0
  122. package/docs/capabilities/jackpotOptOut.md +92 -0
  123. package/docs/capabilities/joinClan.md +169 -0
  124. package/docs/capabilities/markAllInboxMessagesAsRead.md +72 -0
  125. package/docs/capabilities/markInboxMessageAsRead.md +69 -0
  126. package/docs/capabilities/markUnmarkInboxMessageAsFavorite.md +75 -0
  127. package/docs/capabilities/miniGameWinAcknowledgeRequest.md +98 -0
  128. package/docs/capabilities/playMiniGame.md +217 -0
  129. package/docs/capabilities/playMiniGameBatch.md +129 -0
  130. package/docs/capabilities/registerInTournament.md +187 -0
  131. package/docs/capabilities/reportClickEvent.md +74 -0
  132. package/docs/capabilities/reportImpressionEvent.md +67 -0
  133. package/docs/capabilities/requestMissionClaimReward.md +117 -0
  134. package/docs/capabilities/requestMissionOptIn.md +98 -0
  135. package/docs/capabilities/requestRaffleOptin.md +108 -0
  136. package/docs/capabilities/setAvatar.md +132 -0
  137. package/docs/capabilities/smarticoCallbacks.md +165 -0
  138. package/docs/capabilities/smarticoGlobal.md +62 -0
  139. package/package.json +3 -2
  140. package/readme-smartico-dev.md +208 -0
  141. package/scripts/capture-responses-browser.mjs +301 -0
  142. package/scripts/gen-capabilities.js +368 -0
  143. package/scripts/run-public-api.mjs +105 -0
  144. package/src/MiniGames/SAWGetTemplatesResponse.ts +2 -0
  145. package/src/MiniGames/SAWTemplate.ts +5 -0
  146. package/src/NodeCache.ts +8 -0
  147. package/src/OCache.ts +17 -0
  148. package/src/SmarticoGlobal.ts +0 -7
  149. package/src/WSAPI/WSAPI.ts +3 -3
  150. package/src/WSAPI/WSAPIJackpots.ts +4 -1
  151. package/src/WSAPI/WSAPIMiniGames.ts +1 -1
  152. package/src/WSAPI/WSAPITypes.ts +44 -0
  153. package/src/WSAPI/WSAPIUser.ts +30 -5
@@ -0,0 +1,117 @@
1
+ # requestMissionClaimReward — API (TMissionClaimRewardResult)
2
+
3
+ > Claim the prize for a completed mission.
4
+ > Import: `import { TMissionClaimRewardResult } from '@smartico/public-api'`
5
+ > Search terms: requestMissionClaimReward, missions, TMissionClaimRewardResult
6
+
7
+ ## Signature
8
+ ```ts
9
+ _smartico.api.requestMissionClaimReward(mission_id: number, ach_completed_id: number): Promise<TMissionClaimRewardResult>
10
+ ```
11
+
12
+ ## Parameters
13
+ - `mission_id` — The mission `ach_id` (from `getMissions()`).
14
+ - `ach_completed_id` — The completion-row identifier, read from `mission.ach_completed_id` on the same mission object fetched via `getMissions()`. Never fabricate or cache across sessions.
15
+
16
+ ## Returns — `Promise<TMissionClaimRewardResult>`
17
+ `TMissionClaimRewardResult`:
18
+ - `err_code` (number) — Error code. `0` = success (rewards credited). See `requestMissionClaimReward` TSDoc for the full table.
19
+ - `err_message` (string) — Optional error message; populated on non-zero `err_code`.
20
+
21
+ ## Behavioral contract
22
+ **Preconditions**
23
+ Only call when, on the mission object from `getMissions()`:
24
+ - `is_completed === true`
25
+ - `requires_prize_claim === true`
26
+ - `prize_claimed_date_ts == null` (i.e. not already claimed)
27
+ - `prize_claim_expiration_date` is `null` OR still in the future
28
+
29
+ The `ach_completed_id` argument must be passed straight from the same
30
+ mission object (`mission.ach_completed_id`). It is a server-side primary
31
+ key identifying the specific completion row; the SDK consumer should
32
+ never synthesise or cache it across sessions — always re-read it from a
33
+ fresh `getMissions()` result.
34
+
35
+
36
+
37
+ **Recurring missions**
38
+ The server transparently handles both one-shot and recurring mission
39
+ completions. The SDK consumer passes a single `ach_completed_id`
40
+ regardless of mission type; the server resolves the correct completion.
41
+
42
+ **Refresh after success**
43
+ On any claim response (success OR failure), the SDK automatically
44
+ re-fetches the mission list and fires any `onUpdate` callback
45
+ registered via `getMissions({ onUpdate })`. No manual re-fetch needed.
46
+ Note: points balance, badges, and level state arrive through their
47
+ own push channels — subscribe to them separately if your UI shows
48
+ those values.
49
+
50
+ **Idempotency**: not idempotent at the row level. A second call on the
51
+ same `ach_completed_id` returns `40017` (already claimed). For a stale
52
+ `ach_completed_id` the second call returns `1`. Guard the call site
53
+ against double-clicks; the SDK does not enforce its own in-flight lock.
54
+
55
+ **Side effects** (consumer-observable effects of a successful claim):
56
+ - Points credited to the user's balance.
57
+ - CRM-rule activities executed (may grant bonuses, badges; may unlock
58
+ follow-up missions, which arrive as a later mission auto-refresh).
59
+ - Analytics / automation events fired downstream; not directly observable
60
+ in the response, but visible via the mission auto-refresh and any
61
+ subsequent bonus / badge updates.
62
+
63
+ **UI guidance**: see [UI Guide — `requestMissionClaimReward`](../../docs/ui/missions/UIGuide_requestMissionClaimReward.md).
64
+
65
+ ## Example
66
+ ```ts
67
+ const missions = await window._smartico.api.getMissions({
68
+ onUpdate: (m) => console.log('[smartico] mission list updated — re-render mission UI from this new array', m),
69
+ });
70
+ const mission = missions.find(m => m.ach_id === missionId);
71
+
72
+ if (
73
+ !mission ||
74
+ !mission.is_completed ||
75
+ !mission.requires_prize_claim ||
76
+ mission.prize_claimed_date_ts ||
77
+ (mission.prize_claim_expiration_date && Date.now() >= mission.prize_claim_expiration_date)
78
+ ) {
79
+ console.log('[smartico] claim not applicable — keep claim button hidden');
80
+ return;
81
+ }
82
+
83
+ console.log('[smartico] claim starting — show loading spinner on claim button and disable it to prevent double-clicks');
84
+ const r = await window._smartico.api.requestMissionClaimReward(mission.ach_id, mission.ach_completed_id);
85
+ console.log('[smartico] claim response received — clear loading spinner');
86
+
87
+ if (r.err_code === 0 || r.err_code === 40017) {
88
+ console.log('[smartico] claim succeeded (or was already claimed) — points/bonuses are credited; mission list auto-refresh will fire via the onUpdate above; hide the claim button');
89
+ } else if (r.err_code === 40015) {
90
+ console.error('[smartico] claim window expired — show a "claim period ended" message and remove the claim button:', mission.prize_claim_expiration_date);
91
+ } else if (r.err_code === 40016) {
92
+ console.error('[smartico] mission reported as not completed by server — local state was stale; auto-refresh will reconcile, do not retry');
93
+ } else {
94
+ console.error('[smartico] claim failed — show an error toast with this message to the user (and re-fetch missions to recover from a stale ach_completed_id):', r.err_message);
95
+ }
96
+ ```
97
+
98
+ ## Errors
99
+ **Error codes** (in `err_code`)
100
+ - `0` — success; the prize was claimed and rewards have been credited.
101
+ - `1` — generic server error. Covers several distinct underlying
102
+ conditions, all collapsed into the same code: stale or wrong
103
+ `ach_completed_id` (does not match user / mission), the mission no
104
+ longer requiring a prize claim, the mission being archived/draft,
105
+ label mismatch, or the completion being too old (server enforces a
106
+ freshness window of several months). Recovery: re-fetch missions
107
+ with `getMissions()`; if the mission still appears claimable,
108
+ surface a generic error.
109
+ - `40015` — claim window expired (`prize_claim_expiration_date` has
110
+ passed). Show a "claim period ended" message; do not retry.
111
+ - `40016` — mission is not completed yet. Indicates a race or a stale
112
+ local cache. Re-fetch via `getMissions()`; if `is_completed` is still
113
+ false, the UI should hide the claim button.
114
+ - `40017` — prize already claimed. Treat as idempotent success: refresh
115
+ the mission list (auto-refresh will fire) and hide the claim button.
116
+ Usually means another tab/session already claimed it.
117
+ - other non-zero — generic server error. Surface `err_message` if any.
@@ -0,0 +1,98 @@
1
+ # requestMissionOptIn — API (TMissionOptInResult)
2
+
3
+ > Opt the current user in to a mission.
4
+ > Import: `import { TMissionOptInResult } from '@smartico/public-api'`
5
+ > Search terms: requestMissionOptIn, missions, TMissionOptInResult, err_code, err_message
6
+
7
+ ## Signature
8
+ ```ts
9
+ _smartico.api.requestMissionOptIn(mission_id: number): Promise<TMissionOptInResult>
10
+ ```
11
+
12
+ ## Parameters
13
+ - `mission_id` — The mission `id` (from `getMissions()`)
14
+
15
+ ## Returns — `Promise<TMissionOptInResult>`
16
+ `TMissionOptInResult`:
17
+ - `err_code` (number) — Error code. `0` = success. See `requestMissionOptIn` TSDoc for the full table.
18
+ - `err_message` (string) — Optional error message; populated on non-zero `err_code`.
19
+
20
+ ## Behavioral contract
21
+ **Preconditions**
22
+ Only call when the mission has `is_requires_optin === true`,
23
+ `is_opted_in === false`, and `is_locked === false`. Calling on a
24
+ mission that does not require opt-in is wasted; calling twice returns
25
+ `40010`.
26
+
27
+
28
+
29
+ **Time-limited missions**
30
+ For missions with `time_limit_ms > 0`, the countdown begins at opt-in
31
+ time, not at mission creation. Server records expiration as
32
+ `optin_date + time_limit_ms`.
33
+
34
+ **Refresh after success**
35
+ The SDK refreshes its mission cache automatically on opt-in response;
36
+ any `onUpdate` callback passed to a prior `getMissions({ onUpdate })`
37
+ fires with the new state shortly after. No manual re-fetch needed.
38
+
39
+ **Idempotency**: not idempotent. A second call returns `40010`. Guard
40
+ the call site against double-clicks.
41
+
42
+ **Side effects**: does NOT award points / badges / levels directly.
43
+ Rewards come from task completion, which is itself gated on opt-in.
44
+ May affect visibility of other missions whose visibility conditions
45
+ depend on this opt-in.
46
+
47
+ **UI guidance**: see [UI Guide — `requestMissionOptIn`](../../docs/ui/missions/UIGuide_requestMissionOptIn.md).
48
+
49
+ **Visitor mode: not supported**
50
+
51
+ ## Example
52
+ ```ts
53
+ const missions = await window._smartico.api.getMissions({
54
+ onUpdate: (m) => console.log('[smartico] mission list updated — re-render mission UI from this new array', m),
55
+ });
56
+ const mission = missions.find(m => m.id === missionId);
57
+
58
+ if (!mission || !mission.is_requires_optin || mission.is_opted_in || mission.is_locked) {
59
+ console.log('[smartico] opt-in not applicable — keep UI as-is');
60
+ return;
61
+ }
62
+
63
+ console.log('[smartico] opt-in starting — show loading spinner on opt-in button and disable it to prevent double-clicks');
64
+ const r = await window._smartico.api.requestMissionOptIn(mission.id);
65
+ console.log('[smartico] opt-in response received — clear loading spinner');
66
+
67
+ if (r.err_code === 0 || r.err_code === 40010) {
68
+ console.log('[smartico] opt-in succeeded (or was already done) — onUpdate above will fire with refreshed mission state; no manual re-fetch needed');
69
+ } else if (r.err_code === 40014) {
70
+ console.error('[smartico] mission is locked — surface the unlock description as guidance:', mission.unlock_mission_description);
71
+ } else {
72
+ console.error('[smartico] opt-in failed — show an error toast with this message to the user:', r.err_message);
73
+ }
74
+ ```
75
+
76
+ ### Example response (REAL shape)
77
+ > Where this real payload differs from the typed Returns above (TS interface vs raw wire), the REAL shape is the runtime truth.
78
+ ```json
79
+ {
80
+ "err_code": 0,
81
+ "err_message": ""
82
+ }
83
+ ```
84
+
85
+ ## Errors
86
+ **Error codes** (in `err_code`)
87
+ - `0` — success; task progress counting begins
88
+ - `105` — wrong mission id (different label) OR visibility conditions
89
+ not met. Same code covers both; use `err_message` to disambiguate.
90
+ - `40010` — already opted-in. Safe to treat as "no-op success"; usually
91
+ means local mission state was stale (e.g. user opted in from another
92
+ session/tab).
93
+ - `40013` — mission not opt-in-able: missing `requires_optin`, in
94
+ DRAFT/ARCHIVED state, or outside its `active_from_ts` /
95
+ `active_till_ts` window.
96
+ - `40014` — mission is locked; user has unlock-tasks remaining.
97
+ Surface the mission's `unlock_mission_description` to guide them.
98
+ - other non-zero — generic server error. Surface `err_message` if any.
@@ -0,0 +1,108 @@
1
+ # requestRaffleOptin — API (TRaffleOptinResponse)
2
+
3
+ > Opts the current user into a specific raffle draw run.
4
+ > Import: `import { TRaffleOptinResponse } from '@smartico/public-api'`
5
+ > Search terms: requestRaffleOptin, raffles, TRaffleOptinResponse
6
+
7
+ ## Signature
8
+ ```ts
9
+ _smartico.api.requestRaffleOptin(props: { raffle_id: number; draw_id: number; raffle_run_id: number }): Promise<TRaffleOptinResponse>
10
+ ```
11
+
12
+ ## Parameters
13
+ - `props.raffle_id` — The parent raffle's `id`.
14
+ - `props.draw_id` — The draw's schedule_id (`TRaffleDraw.id`).
15
+ - `props.raffle_run_id` — The run instance ID (`TRaffleDraw.run_id`).
16
+
17
+ ## Returns — `Promise<TRaffleOptinResponse>`
18
+ `TRaffleOptinResponse`:
19
+ - `err_code` (number) — Error code. `0` = success. See `requestRaffleOptin` TSDoc for the full table.
20
+ - `err_message` (string) — Optional error message; populated on non-zero `err_code`.
21
+
22
+ ## Behavioral contract
23
+ **Preconditions**
24
+ Read the candidate draw from `getRaffles`'s embedded
25
+ `draws[]` and gate the call on
26
+ `requires_optin === true && !user_opted_in && is_active &&
27
+ current_state !== Executed`. Calling without these guards may
28
+ return a non-zero `err_code`.
29
+
30
+ **Argument mapping** — the three IDs come from different fields:
31
+ - `raffle_id` — the parent raffle's `TRaffle.id`
32
+ - `draw_id` — `TRaffleDraw.id` (schedule_id, stable across runs)
33
+ - `raffle_run_id` — `TRaffleDraw.run_id` (instance ID for this
34
+ specific run)
35
+
36
+
37
+
38
+ **Idempotency**: NOT idempotent. A second call on the same
39
+ `raffle_run_id` returns `err_code === 1` with `err_message`
40
+ indicating the user is already opted in. Treat as success in
41
+ the UI — the underlying state is what the consumer wants.
42
+ Guard the call site against double-clicks.
43
+
44
+ **Refresh after success (and after failure)**
45
+ The SDK automatically refreshes the raffles cache on every
46
+ response and fires the `onUpdate` callback registered via
47
+ `getRaffles`. After `err_code === 0`, the affected draw's
48
+ `user_opted_in` flips to `true` on the refreshed list.
49
+
50
+ **Side effects** (on `err_code === 0`)
51
+ - The user is registered for this run. Tickets earned within
52
+ the run's eligibility window will participate in the draw.
53
+ - No balance change. No CRM-side rewards. Opt-in is a metadata
54
+ operation only.
55
+
56
+ **Throws**
57
+ `raffle_id`, `draw_id`, and `raffle_run_id` are all required —
58
+ the SDK throws synchronously when any is missing or falsy.
59
+
60
+ **UI guidance**: see [UI Guide — `requestRaffleOptin`](../../docs/ui/raffles/UIGuide_requestRaffleOptin.md).
61
+
62
+ **Visitor mode**: not supported.
63
+
64
+ ## Example
65
+ ```ts
66
+ const raffles = await window._smartico.api.getRaffles({
67
+ onUpdate: (refreshed) => console.log('[smartico] raffles refreshed — re-render', refreshed),
68
+ });
69
+ const raffle = raffles[0];
70
+ const draw = raffle.draws.find(d =>
71
+ d.requires_optin && !d.user_opted_in && d.is_active && d.current_state !== 3
72
+ );
73
+
74
+ if (!draw) {
75
+ console.log('[smartico] no opt-in-required draw available — keep CTA hidden');
76
+ return;
77
+ }
78
+
79
+ console.log('[smartico] opt-in starting — set in-flight flag, show loading dots on the Opt-in button');
80
+ const r = await window._smartico.api.requestRaffleOptin({
81
+ raffle_id: raffle.id,
82
+ draw_id: draw.id, // schedule_id, NOT run_id
83
+ raffle_run_id: draw.run_id,
84
+ });
85
+ console.log('[smartico] opt-in response received — clear in-flight flag');
86
+
87
+ if (r.err_code === 0) {
88
+ console.log('[smartico] opted in successfully — show "Fully opted in" state on the draw card; onUpdate above will fire with user_opted_in: true');
89
+ } else if (r.err_code === 1 && r.err_message?.toLowerCase().includes('already opted in')) {
90
+ console.log('[smartico] already opted in (perhaps from another tab) — treat as success, show "Fully opted in"');
91
+ } else {
92
+ console.error('[smartico] opt-in failed — surface this error to the user:', r.err_message);
93
+ }
94
+ ```
95
+
96
+ ## Errors
97
+ **Error codes** (in `err_code`)
98
+ - `0` — success; the user is opted into this run. Tickets
99
+ collected after the run's `ticket_start_ts` will participate.
100
+ - `1` — generic opt-in failure. The `err_message` distinguishes
101
+ the specific cause: the draw doesn't require opt-in
102
+ (`requires_optin === false`), `raffle_id` doesn't match the
103
+ `draw_id`, the user is already opted in (or the draw has
104
+ completed), or the user is in a control group for this raffle.
105
+ - other non-zero — generic server error. Surface `err_message`.
106
+
107
+ ## Related
108
+ - `getRaffles`
@@ -0,0 +1,132 @@
1
+ # setAvatar — API (TSetAvatarResult)
2
+
3
+ > Activates the specified avatar for the current user.
4
+ > Import: `import { TSetAvatarResult } from '@smartico/public-api'`
5
+ > Search terms: setAvatar, avatars, TSetAvatarResult, err_code, err_message
6
+
7
+ ## Signature
8
+ ```ts
9
+ _smartico.api.setAvatar(props: { avatar_url: string; avatar_real_id: number }): Promise<TSetAvatarResult>
10
+ ```
11
+
12
+ ## Parameters
13
+ - `props.avatar_url` — Absolute CDN URL of the avatar image. Read from `TAvatarDefinition.url` for catalog avatars or `TAvatarCustomized.url` for AI variants.
14
+ - `props.avatar_real_id` — Numeric ID of the base avatar from `TAvatarDefinition.avatar_real_id`. For AI variants, this is the `avatar_real_id` of the base they were derived from.
15
+
16
+ ## Returns — `Promise<TSetAvatarResult>`
17
+ `TSetAvatarResult`:
18
+ - `err_code` (number) — Error code. `0` = success. See `setAvatar` TSDoc for the full table.
19
+ - `err_message` (string) — Optional error message; populated on non-zero `err_code`.
20
+
21
+ ## Behavioral contract
22
+ **Preconditions**
23
+ - User must be authenticated. Visitor mode is not supported.
24
+ - `avatar_url` must be non-empty and `avatar_real_id` must be truthy — the SDK
25
+ throws synchronously otherwise (the request never reaches the server).
26
+ - The avatar must exist in the catalog from `getAvatarsList` (or be an AI
27
+ variant of a base avatar the user already owns). Free avatars
28
+ (`avatar_source_type_id === 0`) and the user's currently active avatar bypass the
29
+ ownership check; all others require `is_given === true`.
30
+
31
+
32
+
33
+ **Refresh after success**
34
+ - The SDK clears both the `getAvatarsList` and `getAvatarsCustomized` caches —
35
+ the next call to either returns fresh data with the new `is_in_use` flag set on
36
+ the chosen avatar.
37
+ - The server persists the new avatar URL on the user record; `getUserProfile`
38
+ reflects it on the next read in this session.
39
+ - **No push to other open sessions.** A second device / tab the user is logged in
40
+ on will not see the new avatar until it next calls `getUserProfile` or
41
+ re-identifies. Plan UI accordingly.
42
+
43
+ **Idempotency**: safe to retry. Re-applying the same `avatar_real_id` returns
44
+ `err_code: 0` and produces no double side effects (no double-deduction — this
45
+ method does not charge any currency — and no duplicate log entries).
46
+
47
+ **Side effects**: updates the user's stored `avatar_id` / `avatar_real_id`. Does
48
+ NOT cost points, gems, or diamonds — the cost lives on the separate AI
49
+ customization HTTP flow (`getAvatarPrompts`). Does NOT write a user-visible
50
+ entry to `getActivityLog`.
51
+
52
+ **UI guidance**: see [UI Guide — `setAvatar`](../../docs/ui/avatars/UIGuide_setAvatar.md).
53
+
54
+ **Visitor mode**: not supported.
55
+
56
+ ## Example
57
+ ```ts
58
+ const avatars = await window._smartico.api.getAvatarsList();
59
+ const target = avatars.find((a) => a.avatar_real_id === 7);
60
+
61
+ if (!target) {
62
+ console.error('[smartico] avatar 7 not in catalog — hide the picker entry');
63
+ return;
64
+ }
65
+
66
+ const isLocked = !target.is_given && target.avatar_source_type_id !== 0;
67
+ if (isLocked) {
68
+ console.log('[smartico] avatar is locked — show "earn this first" prompt instead of calling setAvatar');
69
+ return;
70
+ }
71
+
72
+ const r = await window._smartico.api.setAvatar({
73
+ avatar_url: target.avatar_url,
74
+ avatar_real_id: target.avatar_real_id,
75
+ });
76
+
77
+ switch (r.err_code) {
78
+ case 0:
79
+ console.log('[smartico] avatar applied — close picker, refresh header avatar');
80
+ break;
81
+ case 1:
82
+ console.error('[smartico] avatar not in catalog — refresh catalog and show error');
83
+ break;
84
+ case 2:
85
+ console.error('[smartico] avatar inactive — operator disabled it; hide from picker');
86
+ break;
87
+ case 3:
88
+ console.error('[smartico] outside time window — show "available on X" message');
89
+ break;
90
+ case 4:
91
+ console.error('[smartico] not owned — show unlock requirements');
92
+ break;
93
+ default:
94
+ console.error('[smartico] avatar apply failed — show generic error toast:', r.err_message);
95
+ }
96
+ ```
97
+
98
+ ### Example response (REAL shape)
99
+ > Where this real payload differs from the typed Returns above (TS interface vs raw wire), the REAL shape is the runtime truth.
100
+ ```json
101
+ {
102
+ "err_code": 4,
103
+ "err_message": "Avatar is not available"
104
+ }
105
+ ```
106
+
107
+ ## Errors
108
+ **Error codes** (in `err_code`)
109
+ - `0` — success; cache is cleared and the profile avatar updates immediately.
110
+ - `1` — avatar not found in the catalog. The `avatar_real_id` doesn't exist for
111
+ this label.
112
+ - `2` — avatar inactive (deactivated by the operator).
113
+ - `3` — outside the avatar's active time window
114
+ (`active_from_date` / `active_till_date`).
115
+ - `4` — user does not own this avatar (it isn't in their `is_given` set and isn't
116
+ a free / default avatar).
117
+ - other non-zero — generic server error; surface `err_message` if present.
118
+
119
+ The default Smartico UI shows a hardcoded "Failed to apply avatar" toast on any
120
+ non-zero `err_code` and does not surface `err_message`. Custom UIs SHOULD branch
121
+ on the code and prefer `err_message` when present (it is the localized server
122
+ string).
123
+
124
+ ## Related
125
+ - `getUserProfile`
126
+ - `TAvatarDefinition.url`
127
+ - `TAvatarCustomized.url`
128
+ - `getAvatarsList`
129
+ - `getAvatarPrompts`
130
+ - `getActivityLog`
131
+ - `TAvatarDefinition.avatar_real_id`
132
+ - `TSetAvatarResult`
@@ -0,0 +1,165 @@
1
+ # _smartico.on — events & callbacks
2
+
3
+ > _smartico.on — events & callbacks.
4
+ > Search terms: on, off, callbacks, events, subscribe, subscribeUpdate, onWin, onReady, props_change, identify, EXTERNAL_CALLBACK, lifecycle, _smartico.on
5
+
6
+ Beyond the request/response `_smartico.api.*` methods, the SDK emits **lifecycle
7
+ and engagement events** you can subscribe to. Register a handler with
8
+ `_smartico.on(...)` and it fires whenever that event occurs — user identified,
9
+ balance changed, gamification widget opened, mini-game won, jackpot hit, etc.
10
+
11
+ This is the push side of the SDK: instead of polling, you react to events as
12
+ they happen.
13
+
14
+ ## Registering and removing handlers
15
+
16
+ ```js
17
+ // Subscribe (works after smartico.js has loaded)
18
+ _smartico.on('identify', (errCode, props) => {
19
+ console.log('[smartico] user identified — render the logged-in UI');
20
+ });
21
+
22
+ // The queue form also works BEFORE the library finishes loading — the call
23
+ // is queued and replayed once smartico.js is ready. Use this when wiring
24
+ // handlers in your page <head> before the script loads.
25
+ _smartico('on', 'identify', (errCode, props) => { /* ... */ });
26
+
27
+ // Remove a specific handler
28
+ function onProps(props) { /* ... */ }
29
+ _smartico.on('props_change', onProps);
30
+ _smartico.off('props_change', onProps);
31
+
32
+ // Passing null removes ALL handlers registered for that key
33
+ _smartico.on('props_change', null);
34
+ ```
35
+
36
+ ### Behavior
37
+
38
+ - **Multiple handlers per event stack.** Calling `on` repeatedly for the same
39
+ key adds handlers; they all fire. Use `off(key, fn)` to remove one, or
40
+ `on(key, null)` to clear all for that key.
41
+ - **Handlers fire asynchronously** (on the next tick) and are isolated — a
42
+ handler that throws logs a warning and does NOT prevent the other handlers
43
+ (or the SDK) from running. Don't rely on execution order between handlers.
44
+ - **Works in both authenticated and visitor mode.** A handler registered via
45
+ `_smartico.on(...)` is active whether the session is a logged-in user or a
46
+ visitor (`_smartico.vapi(...)`). Events that require an account (`identify`,
47
+ `login`, `logout`) simply never fire in visitor mode — see the per-event
48
+ notes below.
49
+ - **Late subscription misses past events.** `on` does not replay events that
50
+ already happened. If you subscribe to `init` after the library has already
51
+ initialized, your handler won't be called. For one-time lifecycle events
52
+ (`init`, `identify`), register early (use the `_smartico('on', ...)` queue
53
+ form in your page head).
54
+
55
+ ## Event reference
56
+
57
+ The first argument of `_smartico.on(...)` is the event key — one of the
58
+ strings below.
59
+
60
+ ### Lifecycle
61
+
62
+ | Event key | Fires when | Handler arguments |
63
+ |---|---|---|
64
+ | `init` | The SDK has finished loading and initializing. Fires shortly after `_smartico.init(...)`, **before** the user is identified. | `(errCode)` — `0` on success |
65
+ | `label_init_completed` | The label configuration / settings have loaded (the handshake that follows `init`). At this point gamification products are known. | `(errCode, message)` |
66
+ | `identify` | A user identify attempt completes — **both success and failure**. Branch on `errCode`. | `(errCode, props, message)` on success; `(errCode, {})` on failure. Not fired in visitor mode. |
67
+ | `login` | A login completes successfully. | `()` — no arguments. Not fired in visitor mode. |
68
+ | `logout` | A logout completes successfully. | `()` — no arguments. Not fired in visitor mode. |
69
+
70
+ ### User state
71
+
72
+ | Event key | Fires when | Handler arguments |
73
+ |---|---|---|
74
+ | `props_change` | Any public user property changes — points, level, balances (gems/diamonds), avatar, unread inbox count, nickname, etc. Fires once right after identify with the full initial set, then again on each change with the changed subset. | `(props)` — a partial public-properties object containing the changed fields. `avatar_id` is returned as a fully-qualified URL. |
75
+ | `page_navigation` | A page load or SPA route change is detected. | `({ url, prev_url, referrer, source })` — `source` is `'load'` (initial page load) or the navigation trigger. |
76
+ | `session_based_dp_detected` | A deep link stored earlier in the browser session is detected after identify (and is about to be executed). | `()` — no arguments. |
77
+
78
+ ### Gamification widget lifecycle
79
+
80
+ | Event key | Fires when | Handler arguments |
81
+ |---|---|---|
82
+ | `gf_starting` | The main gamification widget begins opening (e.g. the user taps the gamification entry point or a deep link opens it). | `()` |
83
+ | `gf_started` | The gamification widget has rendered and is displayed to the user. Fires after `gf_starting`. | `()` |
84
+ | `gf_closing` | The gamification widget (or a standalone mini-game) begins closing. | `()` |
85
+ | `saw_starting` | A standalone mini-game surface (Spin-a-Wheel / MatchX / Quiz) begins opening. | `()` |
86
+ | `inbox_starting` | The standalone inbox widget begins opening. | `()` |
87
+ | `gf_ux` | A screen-view / UX analytics event occurs inside the gamification widget (the user navigates to a screen or section). Use to mirror in-widget navigation into your own analytics. | `({ screen_name_id, custom_section_id, entity_id, screen_subname_id })` |
88
+
89
+ ### Wins and game launches
90
+
91
+ | Event key | Fires when | Handler arguments |
92
+ |---|---|---|
93
+ | `mini_game_win` | A mini-game spin finishes and a prize is determined. Fires for both real and visitor-mode plays. | `({ prize_id, name, visitor_win_uuid })` — `name` is the prize display name. In visitor mode, `visitor_win_uuid` can be passed to `_smartico.convertVisitorGame(uuid)` to attach the win to a real account on registration. |
94
+ | `jackpot_win` | A jackpot the user participates in is hit (the pot explodes and the user is among the recipients). | `(message)` — the win payload (winner details + jackpot info). See the Jackpots UI guide (`docs/ui/jackpots/`) for how the default Smartico UI surfaces wins. |
95
+ | `ach_game_opening` | The user taps a related / eligible casino game tile from inside the gamification widget (mission, tournament, jackpot, or store context). Use this to launch the game in your own casino lobby. | `(game)` — the game object (catalog id, name, launch links, plus a `context` field naming where it was opened from). If you do not handle this event, the default Smartico UI opens the game's configured link itself. |
96
+
97
+ ### Errors
98
+
99
+ | Event key | Fires when | Handler arguments |
100
+ |---|---|---|
101
+ | `protocol_error` | The server rejected a request as an unsupported command (a protocol-level error, distinct from a method's `err_code`). | `({ errCode, errMsg })` |
102
+
103
+ ## Examples
104
+
105
+ ### Keep a balance widget live
106
+
107
+ ```js
108
+ // Render once on identify, then patch on every change.
109
+ _smartico.on('identify', (errCode, props) => {
110
+ if (errCode === 0) {
111
+ console.log('[smartico] initial balance — render widget:', props.ach_points_balance);
112
+ } else {
113
+ console.error('[smartico] identify failed — show logged-out state');
114
+ }
115
+ });
116
+
117
+ _smartico.on('props_change', (props) => {
118
+ if (props.ach_points_balance !== undefined) {
119
+ console.log('[smartico] points changed — update the balance widget:', props.ach_points_balance);
120
+ }
121
+ if (props.core_inbox_unread_count !== undefined) {
122
+ console.log('[smartico] unread count changed — update the inbox badge:', props.core_inbox_unread_count);
123
+ }
124
+ });
125
+ ```
126
+
127
+ ### React to a mini-game win
128
+
129
+ ```js
130
+ _smartico.on('mini_game_win', ({ prize_id, name, visitor_win_uuid }) => {
131
+ console.log('[smartico] user won prize', prize_id, '—', name, '— show your own celebration overlay');
132
+
133
+ if (visitor_win_uuid) {
134
+ console.log('[smartico] visitor win — after the user registers, call _smartico.convertVisitorGame to attach this win');
135
+ }
136
+ });
137
+ ```
138
+
139
+ ### Launch casino games from the gamification widget yourself
140
+
141
+ ```js
142
+ // Take over game launching so games open in your lobby instead of the
143
+ // default link-open behavior.
144
+ _smartico.on('ach_game_opening', (game) => {
145
+ console.log('[smartico] user wants to play game — launch it in your lobby:', game.ext_game_id, '(context:', game.context + ')');
146
+ });
147
+ ```
148
+
149
+ ### Mirror in-widget navigation into your analytics
150
+
151
+ ```js
152
+ _smartico.on('gf_ux', ({ screen_name_id, custom_section_id, entity_id }) => {
153
+ console.log('[smartico] gamification screen view — forward to your analytics:', screen_name_id, custom_section_id, entity_id);
154
+ });
155
+ ```
156
+
157
+ ## Notes
158
+
159
+ - The handler argument shapes above describe what the SDK passes today. Treat
160
+ unfamiliar fields defensively (optional-chain / null-check) — payloads can
161
+ gain fields over time.
162
+ - For request/response data (the current list of missions, the user profile,
163
+ the jackpot pots, etc.), use the `_smartico.api.*` methods (see the API
164
+ reference). Callbacks are for reacting to events; the API methods are for
165
+ fetching and mutating state.