@tiktool/live 2.4.7 → 2.4.9

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/dist/index.d.mts CHANGED
@@ -1,551 +1,3 @@
1
- import { EventEmitter } from 'events';
2
-
3
- interface TikTokUser {
4
- id: string;
5
- nickname: string;
6
- uniqueId: string;
7
- profilePicture?: string;
8
- profilePictureUrl?: string;
9
- badges?: string[];
10
- }
11
- interface BaseEvent {
12
- type: string;
13
- timestamp: number;
14
- msgId: string;
15
- }
16
- interface ChatEvent extends BaseEvent {
17
- type: 'chat';
18
- user: TikTokUser;
19
- comment: string;
20
- }
21
- interface MemberEvent extends BaseEvent {
22
- type: 'member';
23
- user: TikTokUser;
24
- action: number;
25
- }
26
- interface LikeEvent extends BaseEvent {
27
- type: 'like';
28
- user: TikTokUser;
29
- likeCount: number;
30
- totalLikes: number;
31
- }
32
- interface GiftEvent extends BaseEvent {
33
- type: 'gift';
34
- user: TikTokUser;
35
- giftId: number;
36
- giftName: string;
37
- diamondCount: number;
38
- repeatCount: number;
39
- repeatEnd: boolean;
40
- combo: boolean;
41
- giftType: number;
42
- groupId: string;
43
- giftPictureUrl?: string;
44
- }
45
- interface SocialEvent extends BaseEvent {
46
- type: 'social';
47
- user: TikTokUser;
48
- action: 'follow' | 'share' | string;
49
- }
50
- interface RoomUserSeqEvent extends BaseEvent {
51
- type: 'roomUserSeq';
52
- viewerCount: number;
53
- totalViewers: number;
54
- }
55
- interface BattleTeamUser {
56
- user: TikTokUser;
57
- score: number;
58
- }
59
- interface BattleTeam {
60
- hostUserId: string;
61
- score: number;
62
- users: BattleTeamUser[];
63
- hostUser?: TikTokUser;
64
- }
65
- interface BattleEvent extends BaseEvent {
66
- type: 'battle';
67
- battleId: string;
68
- status: number;
69
- battleDuration: number;
70
- teams: BattleTeam[];
71
- battleSettings?: {
72
- startTimeMs?: number;
73
- duration?: number;
74
- endTimeMs?: number;
75
- };
76
- }
77
- interface BattleArmiesEvent extends BaseEvent {
78
- type: 'battleArmies';
79
- battleId: string;
80
- status: number;
81
- teams: BattleTeam[];
82
- battleSettings?: {
83
- startTimeMs?: number;
84
- duration?: number;
85
- endTimeMs?: number;
86
- };
87
- }
88
- interface BattleTaskEvent extends BaseEvent {
89
- type: 'battleTask';
90
- taskAction: number;
91
- battleRefId: string;
92
- missionType: string;
93
- multiplier: number;
94
- missionDuration: number;
95
- missionTarget: number;
96
- remainingSeconds: number;
97
- endTimestampS: number;
98
- timerType: number;
99
- }
100
- interface BarrageEvent extends BaseEvent {
101
- type: 'barrage';
102
- msgType: number;
103
- subType: number;
104
- displayType: number;
105
- duration: number;
106
- defaultPattern: string;
107
- content: string;
108
- }
109
- interface SubscribeEvent extends BaseEvent {
110
- type: 'subscribe';
111
- user: TikTokUser;
112
- subMonth: number;
113
- }
114
- interface EmoteChatEvent extends BaseEvent {
115
- type: 'emoteChat';
116
- user: TikTokUser;
117
- emoteId: string;
118
- emoteUrl: string;
119
- emoteName?: string;
120
- }
121
- interface EnvelopeEvent extends BaseEvent {
122
- type: 'envelope';
123
- envelopeId: string;
124
- diamondCount: number;
125
- }
126
- interface QuestionEvent extends BaseEvent {
127
- type: 'question';
128
- user: TikTokUser;
129
- questionText: string;
130
- }
131
- interface ControlEvent extends BaseEvent {
132
- type: 'control';
133
- action: number;
134
- }
135
- interface RoomEvent extends BaseEvent {
136
- type: 'room';
137
- status: number;
138
- }
139
- interface LiveIntroEvent extends BaseEvent {
140
- type: 'liveIntro';
141
- roomId: string;
142
- title: string;
143
- }
144
- interface RankUpdateEvent extends BaseEvent {
145
- type: 'rankUpdate';
146
- rankType: string;
147
- rankList: Array<{
148
- user: TikTokUser;
149
- rank: number;
150
- score: number;
151
- }>;
152
- }
153
- interface LinkMicEvent extends BaseEvent {
154
- type: 'linkMic';
155
- action: string;
156
- users: TikTokUser[];
157
- }
158
- interface UnknownEvent extends BaseEvent {
159
- type: 'unknown';
160
- method: string;
161
- }
162
- type LiveEvent = ChatEvent | MemberEvent | LikeEvent | GiftEvent | SocialEvent | RoomUserSeqEvent | BattleEvent | BattleArmiesEvent | BattleTaskEvent | BarrageEvent | SubscribeEvent | EmoteChatEvent | EnvelopeEvent | QuestionEvent | ControlEvent | RoomEvent | LiveIntroEvent | RankUpdateEvent | LinkMicEvent | UnknownEvent;
163
- interface TikTokLiveEvents {
164
- connected: () => void;
165
- disconnected: (code: number, reason: string) => void;
166
- roomInfo: (info: RoomInfo) => void;
167
- error: (error: Error) => void;
168
- chat: (event: ChatEvent) => void;
169
- member: (event: MemberEvent) => void;
170
- like: (event: LikeEvent) => void;
171
- gift: (event: GiftEvent) => void;
172
- social: (event: SocialEvent) => void;
173
- roomUserSeq: (event: RoomUserSeqEvent) => void;
174
- battle: (event: BattleEvent) => void;
175
- battleArmies: (event: BattleArmiesEvent) => void;
176
- battleTask: (event: BattleTaskEvent) => void;
177
- barrage: (event: BarrageEvent) => void;
178
- subscribe: (event: SubscribeEvent) => void;
179
- emoteChat: (event: EmoteChatEvent) => void;
180
- envelope: (event: EnvelopeEvent) => void;
181
- question: (event: QuestionEvent) => void;
182
- control: (event: ControlEvent) => void;
183
- room: (event: RoomEvent) => void;
184
- liveIntro: (event: LiveIntroEvent) => void;
185
- rankUpdate: (event: RankUpdateEvent) => void;
186
- linkMic: (event: LinkMicEvent) => void;
187
- unknown: (event: UnknownEvent) => void;
188
- event: (event: LiveEvent) => void;
189
- }
190
- interface RoomInfo {
191
- roomId: string;
192
- wsHost: string;
193
- clusterRegion: string;
194
- connectedAt: string;
195
- ownerUserId?: string;
196
- }
197
- interface TikTokLiveOptions {
198
- uniqueId: string;
199
- signServerUrl?: string;
200
- apiKey: string;
201
- autoReconnect?: boolean;
202
- maxReconnectAttempts?: number;
203
- heartbeatInterval?: number;
204
- debug?: boolean;
205
- webSocketImpl?: any;
206
- /**
207
- * TikTok browser session ID cookie for authenticated connections.
208
- * Enables ranklist API access and authenticated WebSocket features.
209
- * Obtain from the user's tiktok.com browser cookies.
210
- */
211
- sessionId?: string;
212
- /**
213
- * TikTok target IDC region (e.g. 'useast5').
214
- * Required when sessionId is provided — must match the account's region.
215
- */
216
- ttTargetIdc?: string;
217
- }
218
- interface RanklistUser {
219
- /** TikTok user ID */
220
- id_str: string;
221
- /** Display name */
222
- nickname: string;
223
- /** Username (@handle) */
224
- display_id?: string;
225
- unique_id?: string;
226
- /** Avatar thumbnail URLs */
227
- avatar_thumb?: {
228
- url_list: string[];
229
- };
230
- /** Full avatar URLs */
231
- avatar_medium?: {
232
- url_list: string[];
233
- };
234
- /** Follower info */
235
- follow_info?: {
236
- follow_status: number;
237
- follower_count: number;
238
- following_count: number;
239
- };
240
- }
241
- /**
242
- * Entry from online_audience endpoint (in-room top gifters).
243
- * Has explicit `rank` (1-based) and `score` fields.
244
- */
245
- interface OnlineAudienceEntry {
246
- rank: number;
247
- score: number;
248
- user: RanklistUser;
249
- }
250
- /**
251
- * Entry from anchor/rank_list endpoint (leaderboard/gifter rankings).
252
- * Position is the array index. Uses `value` (not `score`).
253
- */
254
- interface AnchorRankListEntry {
255
- /** Gift value (diamonds/coins) */
256
- value: number;
257
- /** Rank category type (e.g. 3 = gifter) */
258
- rank_type: number;
259
- /** Time period type (e.g. 1 = hourly) */
260
- rank_time_type: number;
261
- /** Auto-thanks message configured by anchor */
262
- auto_thanks_message?: string;
263
- /** Schema URL for navigation */
264
- schema_url?: string;
265
- /** Highlight DM share status */
266
- highlight_dm_share_status?: number;
267
- /** Ranked user data */
268
- user: RanklistUser;
269
- }
270
- interface RanklistSelfInfo {
271
- rank: number;
272
- score: number;
273
- gap_description?: string;
274
- }
275
- /** Response from "online_audience" sub-endpoint — in-room top gifters */
276
- interface OnlineAudienceResponse {
277
- status_code: number;
278
- data: {
279
- ranks: OnlineAudienceEntry[];
280
- self_info?: RanklistSelfInfo;
281
- currency?: string;
282
- total?: number;
283
- };
284
- }
285
- /** Response from "anchor_rank_list" sub-endpoint — gifter leaderboard */
286
- interface AnchorRankListResponse {
287
- status_code: number;
288
- data: {
289
- rank_list: AnchorRankListEntry[];
290
- /** Room where ranks were accumulated */
291
- latest_room_id_str?: string;
292
- /** Rank period start (unix timestamp) */
293
- rank_time_begin?: number;
294
- /** Rank period end (unix timestamp) */
295
- rank_time_end?: number;
296
- /** Whether to show rank summary */
297
- show_rank_summary?: boolean;
298
- /** Default rank type for this anchor */
299
- default_rank_type?: number;
300
- };
301
- }
302
- /** Entrance tab info from "entrance" sub-endpoint */
303
- interface EntranceTab {
304
- title: string;
305
- rank_type: number;
306
- list_lynx_type?: number;
307
- }
308
- /** Entrance config for a single rank_type */
309
- interface EntranceInfo {
310
- rank_type: number;
311
- /** Whether the anchor appears in this ranking */
312
- owner_on_rank: boolean;
313
- /** Anchor's position in this ranking (0-based) */
314
- owner_rank_idx?: number;
315
- /** Current score in this ranking */
316
- current_score?: number;
317
- /** Countdown in seconds until ranking resets */
318
- countdown?: number;
319
- /** Window size in seconds (86400 = daily) */
320
- window_size?: number;
321
- /** Unix timestamp when ranking resets */
322
- reset_time?: number;
323
- /** Related tab to show when clicking this entrance */
324
- related_tab_rank_type?: number;
325
- /** Gap description with points needed to reach a rank */
326
- affiliated_content?: {
327
- gap_desc?: {
328
- default_pattern: string;
329
- pieces?: Array<{
330
- string_value: string;
331
- type: number;
332
- }>;
333
- };
334
- };
335
- /** Class/League info */
336
- class_info?: {
337
- class_type: number;
338
- star_count: number;
339
- };
340
- }
341
- interface EntranceResponse {
342
- status_code: number;
343
- data: Array<{
344
- group_type?: number;
345
- Priority?: number;
346
- data?: {
347
- tabs?: EntranceTab[];
348
- entrances?: EntranceInfo[];
349
- };
350
- }>;
351
- }
352
- type RanklistResponse = OnlineAudienceResponse | AnchorRankListResponse | EntranceResponse;
353
-
354
- declare class TikTokLive extends EventEmitter {
355
- private ws;
356
- private heartbeatTimer;
357
- private reconnectAttempts;
358
- private intentionalClose;
359
- private _connected;
360
- private _eventCount;
361
- private _roomId;
362
- private _ownerUserId;
363
- private readonly uniqueId;
364
- private readonly signServerUrl;
365
- private readonly apiKey;
366
- private readonly autoReconnect;
367
- private readonly maxReconnectAttempts;
368
- private readonly heartbeatInterval;
369
- private readonly debug;
370
- private _sessionId?;
371
- private _ttTargetIdc?;
372
- constructor(options: TikTokLiveOptions);
373
- connect(): Promise<void>;
374
- disconnect(): void;
375
- get connected(): boolean;
376
- get eventCount(): number;
377
- get roomId(): string;
378
- /** Get the stored session ID (if any) */
379
- get sessionId(): string | undefined;
380
- /** Update the session ID at runtime (e.g. after TikTok login) */
381
- setSession(sessionId: string, ttTargetIdc?: string): void;
382
- /**
383
- * Build a cookie header string for authenticated API requests (e.g. ranklist).
384
- * Returns undefined if no session is set.
385
- */
386
- buildSessionCookieHeader(): string | undefined;
387
- on<K extends keyof TikTokLiveEvents>(event: K, listener: TikTokLiveEvents[K]): this;
388
- once<K extends keyof TikTokLiveEvents>(event: K, listener: TikTokLiveEvents[K]): this;
389
- off<K extends keyof TikTokLiveEvents>(event: K, listener: TikTokLiveEvents[K]): this;
390
- emit<K extends keyof TikTokLiveEvents>(event: K, ...args: Parameters<TikTokLiveEvents[K]>): boolean;
391
- private handleFrame;
392
- private startHeartbeat;
393
- private stopHeartbeat;
394
- }
395
-
396
- interface GetRanklistOptions {
397
- /** API server URL (default: https://api.tik.tools) */
398
- serverUrl?: string;
399
- /** API key for authentication */
400
- apiKey: string;
401
- /** TikTok username to look up (auto-resolves room_id and anchor_id) */
402
- uniqueId?: string;
403
- /** Direct room ID (skip resolution) */
404
- roomId?: string;
405
- /** Direct anchor/owner ID (skip resolution) */
406
- anchorId?: string;
407
- /**
408
- * TikTok session cookie string for authentication.
409
- * Required — ranklist endpoints return 20003 without login.
410
- * Example: "sessionid=abc123; sid_guard=def456"
411
- */
412
- sessionCookie?: string;
413
- /**
414
- * Which ranklist sub-endpoint to call:
415
- * - "online_audience" (default) — top gifters with scores
416
- * - "anchor_rank_list" — gifter ranking by rank_type
417
- * - "entrance" — entrance UI metadata, tabs, gap-to-rank
418
- */
419
- type?: 'online_audience' | 'anchor_rank_list' | 'entrance';
420
- /**
421
- * For "anchor_rank_list" type only:
422
- * - "1" = hourly ranking (default)
423
- * - "8" = daily ranking
424
- */
425
- rankType?: string;
426
- }
427
- /**
428
- * Fetch ranked user lists from TikTok via the sign server.
429
- *
430
- * When `sessionCookie` is provided, the server returns a **sign-and-return**
431
- * response with a signed URL that you must fetch from your own IP
432
- * (TikTok sessions are IP-bound). Check for `sign_and_return: true` in
433
- * the response to detect this mode.
434
- *
435
- * @example
436
- * ```ts
437
- * const data = await getRanklist({
438
- * apiKey: 'your-key',
439
- * uniqueId: 'katarina.live',
440
- * sessionCookie: 'sessionid=abc; sid_guard=def',
441
- * type: 'online_audience',
442
- * });
443
- *
444
- * if (data.sign_and_return) {
445
- * // Fetch the signed URL from YOUR IP with your session cookie
446
- * const resp = await fetch(data.signed_url, {
447
- * method: data.method,
448
- * headers: { ...data.headers, Cookie: sessionCookie },
449
- * ...(data.body ? { body: data.body } : {}),
450
- * });
451
- * const tikData = await resp.json();
452
- * console.log(tikData); // TikTok's raw response
453
- * } else {
454
- * console.log(data); // Direct TikTok response (no session)
455
- * }
456
- * ```
457
- */
458
- declare function getRanklist(opts: GetRanklistOptions): Promise<RanklistResponse>;
459
-
460
- interface GetRegionalRanklistOptions {
461
- /** API server URL (default: https://api.tik.tools) */
462
- serverUrl?: string;
463
- /** API key for authentication (Pro or Ultra tier required) */
464
- apiKey: string;
465
- /** TikTok username to look up (auto-resolves room_id and anchor_id) */
466
- uniqueId?: string;
467
- /** Direct room ID (skip resolution) */
468
- roomId?: string;
469
- /** Direct anchor/owner ID (skip resolution) */
470
- anchorId?: string;
471
- /**
472
- * Ranking period:
473
- * - "1" = Hourly
474
- * - "8" = Daily (default)
475
- * - "15" = Popular LIVE
476
- * - "16" = League
477
- */
478
- rankType?: '1' | '8' | '15' | '16';
479
- /**
480
- * Sub-endpoint type:
481
- * - "list" (default) — ranked users with scores
482
- * - "entrance" — available ranking tabs/metadata
483
- */
484
- type?: 'list' | 'entrance';
485
- /** Gap interval filter (default: "0") */
486
- gapInterval?: string;
487
- /**
488
- * TikTok session cookie string for authentication.
489
- * Passed to the API server for proxied requests.
490
- * Example: "sessionid=abc123; sessionid_ss=abc123"
491
- */
492
- sessionCookie?: string;
493
- /**
494
- * Client's real IP address (for deployed server scenarios).
495
- * When running on a remote server, pass the end-user's IP so the
496
- * API server can proxy the TikTok request from the correct IP.
497
- */
498
- clientIp?: string;
499
- }
500
- interface RegionalRanklistSignedResponse {
501
- /** Always 0 on success */
502
- status_code: number;
503
- /** Always "fetch_signed_url" */
504
- action: string;
505
- /** The signed TikTok URL to POST */
506
- signed_url: string;
507
- /** HTTP method (always POST) */
508
- method: string;
509
- /** Required headers for the fetch */
510
- headers: Record<string, string>;
511
- /** URL-encoded POST body */
512
- body: string;
513
- /** Cookies to include (ttwid etc.) — append your sessionid */
514
- cookies: string;
515
- /** Human-readable note */
516
- note: string;
517
- }
518
- /**
519
- * Get a signed URL for fetching regional LIVE leaderboard data.
520
- *
521
- * **Two-step pattern**: TikTok sessions are IP-bound, so instead of
522
- * server-side fetching, this returns a signed URL with headers/body
523
- * that you POST from your own IP with your session cookie.
524
- *
525
- * Requires **Pro** or **Ultra** API key tier.
526
- *
527
- * @example
528
- * ```ts
529
- * // Step 1: Get signed URL
530
- * const signed = await getRegionalRanklist({
531
- * apiKey: 'your-pro-key',
532
- * roomId: '7607695933891218198',
533
- * anchorId: '7444599004337652758',
534
- * rankType: '8', // Daily
535
- * });
536
- *
537
- * // Step 2: Fetch from YOUR IP with YOUR session
538
- * const resp = await fetch(signed.signed_url, {
539
- * method: signed.method,
540
- * headers: { ...signed.headers, Cookie: `sessionid=YOUR_SID; ${signed.cookies}` },
541
- * body: signed.body,
542
- * });
543
- * const { data } = await resp.json();
544
- * data.rank_view.ranks.forEach((r, i) =>
545
- * console.log(`${i+1}. ${r.user.nickname} — ${r.score} pts`)
546
- * );
547
- * ```
548
- */
549
- declare function getRegionalRanklist(opts: GetRegionalRanklistOptions): Promise<RegionalRanklistSignedResponse>;
550
-
551
- export { type AnchorRankListEntry, type AnchorRankListResponse, type BarrageEvent, type BaseEvent, type BattleArmiesEvent, type BattleEvent, type BattleTaskEvent, type BattleTeam, type BattleTeamUser, type ChatEvent, type ControlEvent, type EmoteChatEvent, type EntranceInfo, type EntranceResponse, type EntranceTab, type EnvelopeEvent, type GetRanklistOptions, type GetRegionalRanklistOptions, type GiftEvent, type LikeEvent, type LinkMicEvent, type LiveEvent, type LiveIntroEvent, type MemberEvent, type OnlineAudienceEntry, type OnlineAudienceResponse, type QuestionEvent, type RankUpdateEvent, type RanklistResponse, type RanklistSelfInfo, type RanklistUser, type RegionalRanklistSignedResponse, type RoomEvent, type RoomInfo, type RoomUserSeqEvent, type SocialEvent, type SubscribeEvent, TikTokLive, type TikTokLiveEvents, type TikTokLiveOptions, type TikTokUser, type UnknownEvent, getRanklist, getRegionalRanklist };
1
+ export { TikTokLive } from './client.js';
2
+ export { GetRanklistOptions, GetRegionalRanklistOptions, RegionalRanklistSignedResponse, getRanklist, getRegionalRanklist } from './api.js';
3
+ export { AnchorRankListEntry, AnchorRankListResponse, BarrageEvent, BaseEvent, BattleArmiesEvent, BattleEvent, BattleTaskEvent, BattleTeam, BattleTeamUser, ChatEvent, ControlEvent, EmoteChatEvent, EntranceInfo, EntranceResponse, EntranceTab, EnvelopeEvent, GiftEvent, LikeEvent, LinkMicEvent, LiveEvent, LiveIntroEvent, MemberEvent, OnlineAudienceEntry, OnlineAudienceResponse, QuestionEvent, RankUpdateEvent, RanklistResponse, RanklistSelfInfo, RanklistUser, RoomEvent, RoomInfo, RoomUserSeqEvent, SocialEvent, SubscribeEvent, TikTokLiveEvents, TikTokLiveOptions, TikTokUser, UnknownEvent } from './types.js';