@rngrow/sdk 0.1.1 → 0.2.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.
package/README.md CHANGED
@@ -58,8 +58,29 @@ const games = await rng.leagues.games({ country: "US" });
58
58
  const gaming = await rng.leagues.gaming({ country: "US", game: "all" });
59
59
  const daily = await rng.leagues.daily({ country: "RO" });
60
60
 
61
- // Creators spiking RIGHT NOW
61
+ // Creators spiking RIGHT NOW, and their spike history
62
62
  const hot = await rng.leagues.hot({ country: "RO" });
63
+ const history = await rng.leagues.hotHistory({ country: "RO", days: 7 });
64
+
65
+ // Creators who fell off a board and are still recruitable (warm leads)
66
+ const dropouts = await rng.leagues.dropouts({ country: "RO", division: "D1" });
67
+
68
+ // Bulk export, JSON or CSV, up to 25,000 rows
69
+ const bulk = await rng.leagues.export({ country: "RO" });
70
+ const csv = await rng.leagues.exportCsv({ country: "RO", source: "gaming" });
71
+ ```
72
+
73
+ ## Gifters and live lookup
74
+
75
+ ```ts
76
+ // The country's biggest gift senders (whales)
77
+ const whales = await rng.gifters.list({ country: "RO", sort: "7d" });
78
+
79
+ // Which creators one gifter funds, and for how much
80
+ const detail = await rng.gifters.detail({ gifterId: whales.gifters[0].gifter_id });
81
+
82
+ // Real-time TikTok lookup: does the handle exist, are they LIVE right now
83
+ const who = await rng.creators.resolve({ username: "somehandle" });
63
84
  ```
64
85
 
65
86
  ## Errors
package/dist/index.cjs CHANGED
@@ -51,6 +51,8 @@ var Rngrow = class {
51
51
  }),
52
52
  /** Discovery volume for a country. */
53
53
  stats: (params) => this.request("/creators/stats", { country: params.country }),
54
+ /** Resolve a TikTok handle in real time: profile + LIVE-right-now status. */
55
+ resolve: (params) => this.request("/creators/resolve", { username: params.username }),
54
56
  /**
55
57
  * Iterate the whole pool with automatic cursor pagination.
56
58
  *
@@ -95,7 +97,36 @@ var Rngrow = class {
95
97
  /** The country's daily (hourly for MENA) diamond ranking. */
96
98
  daily: (params) => this.request("/leagues/daily", params),
97
99
  /** Creators spiking in diamonds right now, across all divisions. */
98
- hot: (params) => this.request("/leagues/hot", params)
100
+ hot: (params) => this.request("/leagues/hot", params),
101
+ /** Past HOT / diamond spike events, up to 30 days back. */
102
+ hotHistory: (params) => this.request("/leagues/hot/history", params),
103
+ /** Creators who fell off a division's board and are still recruitable. */
104
+ dropouts: (params) => this.request("/leagues/dropouts", params),
105
+ /** Bulk board export as JSON, up to 25,000 rows. */
106
+ export: (params) => this.request("/leagues/export", {
107
+ country: params.country,
108
+ source: params.source,
109
+ divisions: params.divisions?.join(","),
110
+ games: params.games?.join(","),
111
+ available_only: params.availableOnly === false ? "false" : void 0,
112
+ max_score: params.maxScore
113
+ }),
114
+ /** Bulk board export as a ready-to-save CSV string. */
115
+ exportCsv: (params) => this.requestText("/leagues/export", {
116
+ country: params.country,
117
+ source: params.source,
118
+ divisions: params.divisions?.join(","),
119
+ games: params.games?.join(","),
120
+ available_only: params.availableOnly === false ? "false" : void 0,
121
+ max_score: params.maxScore,
122
+ format: "csv"
123
+ })
124
+ };
125
+ this.gifters = {
126
+ /** The country's top gift senders (whales), lifetime or rolling 7 days. */
127
+ list: (params) => this.request("/gifters", params),
128
+ /** One gifter's profile and exactly which creators they fund. */
129
+ detail: (params) => this.request(`/gifters/${encodeURIComponent(params.gifterId)}`)
99
130
  };
100
131
  if (!apiKey || !apiKey.startsWith("rng_")) {
101
132
  throw new Error(
@@ -137,6 +168,28 @@ var Rngrow = class {
137
168
  }
138
169
  return body;
139
170
  }
171
+ async requestText(path, query = {}) {
172
+ const url = new URL(this.baseUrl + path);
173
+ for (const [k, v] of Object.entries(query)) {
174
+ if (v !== void 0 && v !== null && v !== "") url.searchParams.set(k, String(v));
175
+ }
176
+ const res = await this.fetchImpl(url.toString(), {
177
+ headers: { "X-API-Key": this.apiKey }
178
+ });
179
+ if (!res.ok) {
180
+ let code = "server_error";
181
+ let message = `Request failed with HTTP ${res.status}`;
182
+ try {
183
+ const body = await res.json();
184
+ if (body?.error?.code) code = body.error.code;
185
+ if (body?.error?.message) message = body.error.message;
186
+ } catch {
187
+ }
188
+ const retryHeader = res.headers.get("Retry-After");
189
+ throw new RngrowError(code, message, res.status, retryHeader ? Number(retryHeader) || void 0 : void 0);
190
+ }
191
+ return res.text();
192
+ }
140
193
  /** Key introspection: plan, countries, rate limits, usage today. */
141
194
  me() {
142
195
  return this.request("/me");
package/dist/index.d.cts CHANGED
@@ -148,6 +148,106 @@ interface HotCreators {
148
148
  count: number;
149
149
  creators: HotCreator[];
150
150
  }
151
+ interface HotEvent {
152
+ division: string;
153
+ username: string | null;
154
+ status: "hot" | "diamond" | string;
155
+ score: number | null;
156
+ diamonds_gained: number | null;
157
+ captured_at: string | null;
158
+ tick_at: string;
159
+ }
160
+ interface HotHistoryPage {
161
+ country: string;
162
+ days: number;
163
+ division?: string;
164
+ username?: string;
165
+ total: number;
166
+ limit: number;
167
+ offset: number;
168
+ count: number;
169
+ events: HotEvent[];
170
+ }
171
+ interface Dropout {
172
+ best_rank: number | null;
173
+ best_score: number | null;
174
+ follower_count: number | null;
175
+ username: string;
176
+ nickname: string | null;
177
+ recruit_status: "available" | "contacted" | string;
178
+ check_age_minutes: number | null;
179
+ dropped_minutes_ago: number | null;
180
+ }
181
+ interface DropoutsResponse {
182
+ country: string;
183
+ division: string;
184
+ count: number;
185
+ dropouts: Dropout[];
186
+ }
187
+ interface ExportResponse {
188
+ country: string;
189
+ source: "league" | "gaming" | "daily";
190
+ count: number;
191
+ truncated: boolean;
192
+ rows: Record<string, unknown>[];
193
+ }
194
+ interface ResolvedCreator {
195
+ username: string;
196
+ nickname: string | null;
197
+ avatar: string | null;
198
+ verified: boolean;
199
+ follower_count: number | null;
200
+ live: boolean;
201
+ }
202
+ type ResolveResponse = {
203
+ found: true;
204
+ creator: ResolvedCreator;
205
+ } | {
206
+ found: false;
207
+ username: string;
208
+ };
209
+ interface Gifter {
210
+ rank: number;
211
+ gifter_id: string;
212
+ username: string;
213
+ diamonds: number;
214
+ est_value_usd: number;
215
+ diamonds_7d: number | null;
216
+ creators_gifted: number | null;
217
+ gifts: number | null;
218
+ last_seen: string | null;
219
+ }
220
+ interface GiftersPage {
221
+ country: string;
222
+ sort: "lifetime" | "7d";
223
+ total_estimated: number | null;
224
+ limit: number;
225
+ offset: number;
226
+ count: number;
227
+ gifters: Gifter[];
228
+ }
229
+ interface GifterDetail {
230
+ gifter: {
231
+ gifter_id: string;
232
+ username: string;
233
+ country: string;
234
+ diamonds: number;
235
+ est_value_usd: number;
236
+ diamonds_7d: number | null;
237
+ diamonds_30d: number | null;
238
+ gifts: number | null;
239
+ creators_gifted: number | null;
240
+ first_seen: string | null;
241
+ last_seen: string | null;
242
+ };
243
+ creators: {
244
+ creator: string;
245
+ diamonds: number;
246
+ est_value_usd: number;
247
+ gifts: number | null;
248
+ last_gifted: string | null;
249
+ }[];
250
+ }
151
251
  declare class RngrowError extends Error {
152
252
  /** Machine-readable error code, e.g. "country_not_in_plan" or "rate_limited". */
153
253
  readonly code: string;
@@ -169,6 +269,7 @@ declare class Rngrow {
169
269
  private readonly fetchImpl;
170
270
  constructor(apiKey: string, options?: RngrowOptions);
171
271
  private request;
272
+ private requestText;
172
273
  /** Key introspection: plan, countries, rate limits, usage today. */
173
274
  me(): Promise<Me>;
174
275
  readonly creators: {
@@ -187,6 +288,10 @@ declare class Rngrow {
187
288
  stats: (params: {
188
289
  country: string;
189
290
  }) => Promise<CreatorStats>;
291
+ /** Resolve a TikTok handle in real time: profile + LIVE-right-now status. */
292
+ resolve: (params: {
293
+ username: string;
294
+ }) => Promise<ResolveResponse>;
190
295
  /**
191
296
  * Iterate the whole pool with automatic cursor pagination.
192
297
  *
@@ -235,7 +340,52 @@ declare class Rngrow {
235
340
  hot: (params: {
236
341
  country: string;
237
342
  }) => Promise<HotCreators>;
343
+ /** Past HOT / diamond spike events, up to 30 days back. */
344
+ hotHistory: (params: {
345
+ country: string;
346
+ days?: number;
347
+ division?: string;
348
+ username?: string;
349
+ limit?: number;
350
+ offset?: number;
351
+ }) => Promise<HotHistoryPage>;
352
+ /** Creators who fell off a division's board and are still recruitable. */
353
+ dropouts: (params: {
354
+ country: string;
355
+ division: string;
356
+ }) => Promise<DropoutsResponse>;
357
+ /** Bulk board export as JSON, up to 25,000 rows. */
358
+ export: (params: {
359
+ country: string;
360
+ source?: "league" | "gaming" | "daily";
361
+ divisions?: string[];
362
+ games?: string[];
363
+ availableOnly?: boolean;
364
+ maxScore?: number;
365
+ }) => Promise<ExportResponse>;
366
+ /** Bulk board export as a ready-to-save CSV string. */
367
+ exportCsv: (params: {
368
+ country: string;
369
+ source?: "league" | "gaming" | "daily";
370
+ divisions?: string[];
371
+ games?: string[];
372
+ availableOnly?: boolean;
373
+ maxScore?: number;
374
+ }) => Promise<string>;
375
+ };
376
+ readonly gifters: {
377
+ /** The country's top gift senders (whales), lifetime or rolling 7 days. */
378
+ list: (params: {
379
+ country: string;
380
+ sort?: "lifetime" | "7d";
381
+ limit?: number;
382
+ offset?: number;
383
+ }) => Promise<GiftersPage>;
384
+ /** One gifter's profile and exactly which creators they fund. */
385
+ detail: (params: {
386
+ gifterId: string;
387
+ }) => Promise<GifterDetail>;
238
388
  };
239
389
  }
240
390
 
241
- export { type Creator, type CreatorStats, type CreatorsPage, type DailyBoard, type GamingBoard, type GamingGame, type HotCreator, type HotCreators, type LeagueAvailableCreator, type LeagueAvailablePage, type LeagueBoard, type LeagueBoardRow, type LeagueCoverage, type LeagueDivision, type Me, type RankingRow, Rngrow, RngrowError, type RngrowOptions, Rngrow as default };
391
+ export { type Creator, type CreatorStats, type CreatorsPage, type DailyBoard, type Dropout, type DropoutsResponse, type ExportResponse, type GamingBoard, type GamingGame, type Gifter, type GifterDetail, type GiftersPage, type HotCreator, type HotCreators, type HotEvent, type HotHistoryPage, type LeagueAvailableCreator, type LeagueAvailablePage, type LeagueBoard, type LeagueBoardRow, type LeagueCoverage, type LeagueDivision, type Me, type RankingRow, type ResolveResponse, type ResolvedCreator, Rngrow, RngrowError, type RngrowOptions, Rngrow as default };
package/dist/index.d.ts CHANGED
@@ -148,6 +148,106 @@ interface HotCreators {
148
148
  count: number;
149
149
  creators: HotCreator[];
150
150
  }
151
+ interface HotEvent {
152
+ division: string;
153
+ username: string | null;
154
+ status: "hot" | "diamond" | string;
155
+ score: number | null;
156
+ diamonds_gained: number | null;
157
+ captured_at: string | null;
158
+ tick_at: string;
159
+ }
160
+ interface HotHistoryPage {
161
+ country: string;
162
+ days: number;
163
+ division?: string;
164
+ username?: string;
165
+ total: number;
166
+ limit: number;
167
+ offset: number;
168
+ count: number;
169
+ events: HotEvent[];
170
+ }
171
+ interface Dropout {
172
+ best_rank: number | null;
173
+ best_score: number | null;
174
+ follower_count: number | null;
175
+ username: string;
176
+ nickname: string | null;
177
+ recruit_status: "available" | "contacted" | string;
178
+ check_age_minutes: number | null;
179
+ dropped_minutes_ago: number | null;
180
+ }
181
+ interface DropoutsResponse {
182
+ country: string;
183
+ division: string;
184
+ count: number;
185
+ dropouts: Dropout[];
186
+ }
187
+ interface ExportResponse {
188
+ country: string;
189
+ source: "league" | "gaming" | "daily";
190
+ count: number;
191
+ truncated: boolean;
192
+ rows: Record<string, unknown>[];
193
+ }
194
+ interface ResolvedCreator {
195
+ username: string;
196
+ nickname: string | null;
197
+ avatar: string | null;
198
+ verified: boolean;
199
+ follower_count: number | null;
200
+ live: boolean;
201
+ }
202
+ type ResolveResponse = {
203
+ found: true;
204
+ creator: ResolvedCreator;
205
+ } | {
206
+ found: false;
207
+ username: string;
208
+ };
209
+ interface Gifter {
210
+ rank: number;
211
+ gifter_id: string;
212
+ username: string;
213
+ diamonds: number;
214
+ est_value_usd: number;
215
+ diamonds_7d: number | null;
216
+ creators_gifted: number | null;
217
+ gifts: number | null;
218
+ last_seen: string | null;
219
+ }
220
+ interface GiftersPage {
221
+ country: string;
222
+ sort: "lifetime" | "7d";
223
+ total_estimated: number | null;
224
+ limit: number;
225
+ offset: number;
226
+ count: number;
227
+ gifters: Gifter[];
228
+ }
229
+ interface GifterDetail {
230
+ gifter: {
231
+ gifter_id: string;
232
+ username: string;
233
+ country: string;
234
+ diamonds: number;
235
+ est_value_usd: number;
236
+ diamonds_7d: number | null;
237
+ diamonds_30d: number | null;
238
+ gifts: number | null;
239
+ creators_gifted: number | null;
240
+ first_seen: string | null;
241
+ last_seen: string | null;
242
+ };
243
+ creators: {
244
+ creator: string;
245
+ diamonds: number;
246
+ est_value_usd: number;
247
+ gifts: number | null;
248
+ last_gifted: string | null;
249
+ }[];
250
+ }
151
251
  declare class RngrowError extends Error {
152
252
  /** Machine-readable error code, e.g. "country_not_in_plan" or "rate_limited". */
153
253
  readonly code: string;
@@ -169,6 +269,7 @@ declare class Rngrow {
169
269
  private readonly fetchImpl;
170
270
  constructor(apiKey: string, options?: RngrowOptions);
171
271
  private request;
272
+ private requestText;
172
273
  /** Key introspection: plan, countries, rate limits, usage today. */
173
274
  me(): Promise<Me>;
174
275
  readonly creators: {
@@ -187,6 +288,10 @@ declare class Rngrow {
187
288
  stats: (params: {
188
289
  country: string;
189
290
  }) => Promise<CreatorStats>;
291
+ /** Resolve a TikTok handle in real time: profile + LIVE-right-now status. */
292
+ resolve: (params: {
293
+ username: string;
294
+ }) => Promise<ResolveResponse>;
190
295
  /**
191
296
  * Iterate the whole pool with automatic cursor pagination.
192
297
  *
@@ -235,7 +340,52 @@ declare class Rngrow {
235
340
  hot: (params: {
236
341
  country: string;
237
342
  }) => Promise<HotCreators>;
343
+ /** Past HOT / diamond spike events, up to 30 days back. */
344
+ hotHistory: (params: {
345
+ country: string;
346
+ days?: number;
347
+ division?: string;
348
+ username?: string;
349
+ limit?: number;
350
+ offset?: number;
351
+ }) => Promise<HotHistoryPage>;
352
+ /** Creators who fell off a division's board and are still recruitable. */
353
+ dropouts: (params: {
354
+ country: string;
355
+ division: string;
356
+ }) => Promise<DropoutsResponse>;
357
+ /** Bulk board export as JSON, up to 25,000 rows. */
358
+ export: (params: {
359
+ country: string;
360
+ source?: "league" | "gaming" | "daily";
361
+ divisions?: string[];
362
+ games?: string[];
363
+ availableOnly?: boolean;
364
+ maxScore?: number;
365
+ }) => Promise<ExportResponse>;
366
+ /** Bulk board export as a ready-to-save CSV string. */
367
+ exportCsv: (params: {
368
+ country: string;
369
+ source?: "league" | "gaming" | "daily";
370
+ divisions?: string[];
371
+ games?: string[];
372
+ availableOnly?: boolean;
373
+ maxScore?: number;
374
+ }) => Promise<string>;
375
+ };
376
+ readonly gifters: {
377
+ /** The country's top gift senders (whales), lifetime or rolling 7 days. */
378
+ list: (params: {
379
+ country: string;
380
+ sort?: "lifetime" | "7d";
381
+ limit?: number;
382
+ offset?: number;
383
+ }) => Promise<GiftersPage>;
384
+ /** One gifter's profile and exactly which creators they fund. */
385
+ detail: (params: {
386
+ gifterId: string;
387
+ }) => Promise<GifterDetail>;
238
388
  };
239
389
  }
240
390
 
241
- export { type Creator, type CreatorStats, type CreatorsPage, type DailyBoard, type GamingBoard, type GamingGame, type HotCreator, type HotCreators, type LeagueAvailableCreator, type LeagueAvailablePage, type LeagueBoard, type LeagueBoardRow, type LeagueCoverage, type LeagueDivision, type Me, type RankingRow, Rngrow, RngrowError, type RngrowOptions, Rngrow as default };
391
+ export { type Creator, type CreatorStats, type CreatorsPage, type DailyBoard, type Dropout, type DropoutsResponse, type ExportResponse, type GamingBoard, type GamingGame, type Gifter, type GifterDetail, type GiftersPage, type HotCreator, type HotCreators, type HotEvent, type HotHistoryPage, type LeagueAvailableCreator, type LeagueAvailablePage, type LeagueBoard, type LeagueBoardRow, type LeagueCoverage, type LeagueDivision, type Me, type RankingRow, type ResolveResponse, type ResolvedCreator, Rngrow, RngrowError, type RngrowOptions, Rngrow as default };
package/dist/index.js CHANGED
@@ -25,6 +25,8 @@ var Rngrow = class {
25
25
  }),
26
26
  /** Discovery volume for a country. */
27
27
  stats: (params) => this.request("/creators/stats", { country: params.country }),
28
+ /** Resolve a TikTok handle in real time: profile + LIVE-right-now status. */
29
+ resolve: (params) => this.request("/creators/resolve", { username: params.username }),
28
30
  /**
29
31
  * Iterate the whole pool with automatic cursor pagination.
30
32
  *
@@ -69,7 +71,36 @@ var Rngrow = class {
69
71
  /** The country's daily (hourly for MENA) diamond ranking. */
70
72
  daily: (params) => this.request("/leagues/daily", params),
71
73
  /** Creators spiking in diamonds right now, across all divisions. */
72
- hot: (params) => this.request("/leagues/hot", params)
74
+ hot: (params) => this.request("/leagues/hot", params),
75
+ /** Past HOT / diamond spike events, up to 30 days back. */
76
+ hotHistory: (params) => this.request("/leagues/hot/history", params),
77
+ /** Creators who fell off a division's board and are still recruitable. */
78
+ dropouts: (params) => this.request("/leagues/dropouts", params),
79
+ /** Bulk board export as JSON, up to 25,000 rows. */
80
+ export: (params) => this.request("/leagues/export", {
81
+ country: params.country,
82
+ source: params.source,
83
+ divisions: params.divisions?.join(","),
84
+ games: params.games?.join(","),
85
+ available_only: params.availableOnly === false ? "false" : void 0,
86
+ max_score: params.maxScore
87
+ }),
88
+ /** Bulk board export as a ready-to-save CSV string. */
89
+ exportCsv: (params) => this.requestText("/leagues/export", {
90
+ country: params.country,
91
+ source: params.source,
92
+ divisions: params.divisions?.join(","),
93
+ games: params.games?.join(","),
94
+ available_only: params.availableOnly === false ? "false" : void 0,
95
+ max_score: params.maxScore,
96
+ format: "csv"
97
+ })
98
+ };
99
+ this.gifters = {
100
+ /** The country's top gift senders (whales), lifetime or rolling 7 days. */
101
+ list: (params) => this.request("/gifters", params),
102
+ /** One gifter's profile and exactly which creators they fund. */
103
+ detail: (params) => this.request(`/gifters/${encodeURIComponent(params.gifterId)}`)
73
104
  };
74
105
  if (!apiKey || !apiKey.startsWith("rng_")) {
75
106
  throw new Error(
@@ -111,6 +142,28 @@ var Rngrow = class {
111
142
  }
112
143
  return body;
113
144
  }
145
+ async requestText(path, query = {}) {
146
+ const url = new URL(this.baseUrl + path);
147
+ for (const [k, v] of Object.entries(query)) {
148
+ if (v !== void 0 && v !== null && v !== "") url.searchParams.set(k, String(v));
149
+ }
150
+ const res = await this.fetchImpl(url.toString(), {
151
+ headers: { "X-API-Key": this.apiKey }
152
+ });
153
+ if (!res.ok) {
154
+ let code = "server_error";
155
+ let message = `Request failed with HTTP ${res.status}`;
156
+ try {
157
+ const body = await res.json();
158
+ if (body?.error?.code) code = body.error.code;
159
+ if (body?.error?.message) message = body.error.message;
160
+ } catch {
161
+ }
162
+ const retryHeader = res.headers.get("Retry-After");
163
+ throw new RngrowError(code, message, res.status, retryHeader ? Number(retryHeader) || void 0 : void 0);
164
+ }
165
+ return res.text();
166
+ }
114
167
  /** Key introspection: plan, countries, rate limits, usage today. */
115
168
  me() {
116
169
  return this.request("/me");
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@rngrow/sdk",
3
- "version": "0.1.1",
3
+ "version": "0.2.0",
4
4
  "description": "Official SDK for the RnG TikTok LIVE Creator API (rngrow.com): recruitable TikTok creators, LIVE league boards, gaming and daily rankings, and real-time HOT signals.",
5
5
  "keywords": [
6
6
  "tiktok",