@hieuxyz/rpc 1.1.0 → 1.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 +56 -22
- package/dist/hieuxyz/Client.d.ts +30 -5
- package/dist/hieuxyz/Client.js +146 -5
- package/dist/hieuxyz/gateway/DiscordWebSocket.d.ts +15 -6
- package/dist/hieuxyz/gateway/DiscordWebSocket.js +72 -36
- package/dist/hieuxyz/gateway/entities/identify.d.ts +12 -1
- package/dist/hieuxyz/gateway/entities/identify.js +7 -6
- package/dist/hieuxyz/gateway/entities/types.d.ts +95 -5
- package/dist/hieuxyz/gateway/entities/types.js +19 -1
- package/dist/hieuxyz/rpc/HieuxyzRPC.d.ts +75 -17
- package/dist/hieuxyz/rpc/HieuxyzRPC.js +144 -21
- package/dist/hieuxyz/rpc/ImageService.d.ts +11 -0
- package/dist/hieuxyz/rpc/ImageService.js +17 -0
- package/dist/hieuxyz/rpc/RpcImage.d.ts +13 -0
- package/dist/hieuxyz/rpc/RpcImage.js +22 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +2 -1
- package/package.json +14 -6
|
@@ -57,7 +57,12 @@ class DiscordWebSocket {
|
|
|
57
57
|
options;
|
|
58
58
|
isReconnecting = false;
|
|
59
59
|
permanentClose = false;
|
|
60
|
+
connectTimeout = null;
|
|
60
61
|
resolveReady = () => { };
|
|
62
|
+
/**
|
|
63
|
+
* Current logged in user info.
|
|
64
|
+
*/
|
|
65
|
+
user = null;
|
|
61
66
|
/**
|
|
62
67
|
* A promise will be resolved when the Gateway connection is ready.
|
|
63
68
|
* and received the READY event.
|
|
@@ -65,8 +70,8 @@ class DiscordWebSocket {
|
|
|
65
70
|
readyPromise;
|
|
66
71
|
/**
|
|
67
72
|
* Create a DiscordWebSocket instance.
|
|
68
|
-
* @param token - Discord user token for authentication.
|
|
69
|
-
* @param options - Configuration options for the WebSocket client.
|
|
73
|
+
* @param {string} token - Discord user token for authentication.
|
|
74
|
+
* @param {DiscordWebSocketOptions} options - Configuration options for the WebSocket client.
|
|
70
75
|
* @throws {Error} If the token is invalid.
|
|
71
76
|
*/
|
|
72
77
|
constructor(token, options) {
|
|
@@ -74,7 +79,11 @@ class DiscordWebSocket {
|
|
|
74
79
|
throw new Error('Invalid token provided.');
|
|
75
80
|
}
|
|
76
81
|
this.token = token;
|
|
77
|
-
this.options =
|
|
82
|
+
this.options = {
|
|
83
|
+
alwaysReconnect: options.alwaysReconnect ?? false,
|
|
84
|
+
properties: options.properties,
|
|
85
|
+
connectionTimeout: options.connectionTimeout ?? 30000,
|
|
86
|
+
};
|
|
78
87
|
this.readyPromise = new Promise((resolve) => (this.resolveReady = resolve));
|
|
79
88
|
}
|
|
80
89
|
resetReadyPromise() {
|
|
@@ -99,39 +108,53 @@ class DiscordWebSocket {
|
|
|
99
108
|
const url = this.resumeGatewayUrl || 'wss://gateway.discord.gg/?v=10&encoding=json';
|
|
100
109
|
logger_1.logger.info(`Attempting to connect to ${url}...`);
|
|
101
110
|
this.ws = new ws_1.default(url);
|
|
111
|
+
this.connectTimeout = setTimeout(() => {
|
|
112
|
+
logger_1.logger.error('Connection timed out. Terminating connection attempt.');
|
|
113
|
+
if (this.ws) {
|
|
114
|
+
this.ws.terminate();
|
|
115
|
+
}
|
|
116
|
+
}, this.options.connectionTimeout);
|
|
102
117
|
this.ws.on('open', () => {
|
|
103
118
|
logger_1.logger.info(`Successfully connected to Discord Gateway at ${url}.`);
|
|
104
119
|
this.isReconnecting = false;
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
logger_1.logger.warn(`Connection closed: ${code} - ${reason.toString('utf-8')}`);
|
|
109
|
-
this.cleanupHeartbeat();
|
|
110
|
-
if (this.permanentClose) {
|
|
111
|
-
logger_1.logger.info('Connection permanently closed by client. Not reconnecting.');
|
|
112
|
-
return;
|
|
113
|
-
}
|
|
114
|
-
if (this.isReconnecting)
|
|
115
|
-
return;
|
|
116
|
-
if (this.shouldReconnect(code)) {
|
|
117
|
-
setTimeout(() => {
|
|
118
|
-
const canResume = code !== 4004 && !!this.sessionId;
|
|
119
|
-
if (!canResume) {
|
|
120
|
-
this.sessionId = null;
|
|
121
|
-
this.sequence = null;
|
|
122
|
-
this.resumeGatewayUrl = null;
|
|
123
|
-
}
|
|
124
|
-
this.connect();
|
|
125
|
-
}, 500);
|
|
126
|
-
}
|
|
127
|
-
else {
|
|
128
|
-
logger_1.logger.info('Not attempting to reconnect based on close code and client options.');
|
|
120
|
+
if (this.connectTimeout) {
|
|
121
|
+
clearTimeout(this.connectTimeout);
|
|
122
|
+
this.connectTimeout = null;
|
|
129
123
|
}
|
|
130
124
|
});
|
|
125
|
+
this.ws.on('message', this.onMessage.bind(this));
|
|
126
|
+
this.ws.on('close', this.handleClose.bind(this));
|
|
131
127
|
this.ws.on('error', (err) => {
|
|
132
|
-
|
|
128
|
+
if (err.message !== 'WebSocket was closed before the connection was established') {
|
|
129
|
+
logger_1.logger.error(`WebSocket Error: ${err.message}`);
|
|
130
|
+
}
|
|
133
131
|
});
|
|
134
132
|
}
|
|
133
|
+
handleClose(code, reason) {
|
|
134
|
+
logger_1.logger.warn(`Connection closed: ${code} - ${reason.toString('utf-8')}`);
|
|
135
|
+
this.cleanupHeartbeat();
|
|
136
|
+
if (this.connectTimeout) {
|
|
137
|
+
clearTimeout(this.connectTimeout);
|
|
138
|
+
this.connectTimeout = null;
|
|
139
|
+
}
|
|
140
|
+
this.isReconnecting = false;
|
|
141
|
+
if (code === 4004) {
|
|
142
|
+
this.sessionId = null;
|
|
143
|
+
this.sequence = null;
|
|
144
|
+
this.resumeGatewayUrl = null;
|
|
145
|
+
}
|
|
146
|
+
if (this.permanentClose) {
|
|
147
|
+
logger_1.logger.info('Connection permanently closed by client. Not reconnecting.');
|
|
148
|
+
return;
|
|
149
|
+
}
|
|
150
|
+
if (this.shouldReconnect(code)) {
|
|
151
|
+
logger_1.logger.info('Attempting to reconnect in 5 seconds...');
|
|
152
|
+
setTimeout(() => this.connect(), 5000);
|
|
153
|
+
}
|
|
154
|
+
else {
|
|
155
|
+
logger_1.logger.info('Not attempting to reconnect based on close code and client options.');
|
|
156
|
+
}
|
|
157
|
+
}
|
|
135
158
|
onMessage(data, isBinary) {
|
|
136
159
|
let decompressedData;
|
|
137
160
|
if (isBinary) {
|
|
@@ -146,6 +169,10 @@ class DiscordWebSocket {
|
|
|
146
169
|
}
|
|
147
170
|
switch (payload.op) {
|
|
148
171
|
case OpCode_1.OpCode.HELLO:
|
|
172
|
+
if (this.connectTimeout) {
|
|
173
|
+
clearTimeout(this.connectTimeout);
|
|
174
|
+
this.connectTimeout = null;
|
|
175
|
+
}
|
|
149
176
|
this.heartbeatIntervalValue = payload.d.heartbeat_interval;
|
|
150
177
|
logger_1.logger.info(`Received HELLO. Setting heartbeat interval to ${this.heartbeatIntervalValue}ms.`);
|
|
151
178
|
this.startHeartbeating();
|
|
@@ -160,12 +187,15 @@ class DiscordWebSocket {
|
|
|
160
187
|
if (payload.t === 'READY') {
|
|
161
188
|
this.sessionId = payload.d.session_id;
|
|
162
189
|
this.resumeGatewayUrl = payload.d.resume_gateway_url + '/?v=10&encoding=json';
|
|
190
|
+
this.user = payload.d.user;
|
|
163
191
|
logger_1.logger.info(`Session READY. Session ID: ${this.sessionId}. Resume URL set.`);
|
|
164
|
-
this.resolveReady();
|
|
192
|
+
this.resolveReady(this.user);
|
|
165
193
|
}
|
|
166
194
|
else if (payload.t === 'RESUMED') {
|
|
167
195
|
logger_1.logger.info('The session has been successfully resumed.');
|
|
168
|
-
this.
|
|
196
|
+
if (this.user) {
|
|
197
|
+
this.resolveReady(this.user);
|
|
198
|
+
}
|
|
169
199
|
}
|
|
170
200
|
break;
|
|
171
201
|
case OpCode_1.OpCode.HEARTBEAT_ACK:
|
|
@@ -211,7 +241,7 @@ class DiscordWebSocket {
|
|
|
211
241
|
logger_1.logger.info(`Heartbeat sent with sequence ${this.sequence}.`);
|
|
212
242
|
}
|
|
213
243
|
identify() {
|
|
214
|
-
const identifyPayload = (0, identify_1.getIdentifyPayload)(this.token);
|
|
244
|
+
const identifyPayload = (0, identify_1.getIdentifyPayload)(this.token, this.options.properties);
|
|
215
245
|
this.sendJson({ op: OpCode_1.OpCode.IDENTIFY, d: identifyPayload });
|
|
216
246
|
logger_1.logger.info('Identify payload sent.');
|
|
217
247
|
}
|
|
@@ -231,7 +261,7 @@ class DiscordWebSocket {
|
|
|
231
261
|
}
|
|
232
262
|
/**
|
|
233
263
|
* Send presence update payload to Gateway.
|
|
234
|
-
* @param presence - Payload update status to send.
|
|
264
|
+
* @param {PresenceUpdatePayload} presence - Payload update status to send.
|
|
235
265
|
*/
|
|
236
266
|
sendActivity(presence) {
|
|
237
267
|
this.sendJson({ op: OpCode_1.OpCode.PRESENCE_UPDATE, d: presence });
|
|
@@ -247,7 +277,7 @@ class DiscordWebSocket {
|
|
|
247
277
|
}
|
|
248
278
|
/**
|
|
249
279
|
* Closes the WebSocket connection.
|
|
250
|
-
* @param force If true, prevents any automatic reconnection attempts.
|
|
280
|
+
* @param {boolean} force If true, prevents any automatic reconnection attempts.
|
|
251
281
|
*/
|
|
252
282
|
close(force = false) {
|
|
253
283
|
if (force) {
|
|
@@ -257,9 +287,13 @@ class DiscordWebSocket {
|
|
|
257
287
|
else {
|
|
258
288
|
logger_1.logger.info('Closing connection manually...');
|
|
259
289
|
}
|
|
260
|
-
this.isReconnecting = false;
|
|
261
290
|
if (this.ws) {
|
|
262
|
-
this.ws.
|
|
291
|
+
if (this.ws.readyState === ws_1.default.OPEN) {
|
|
292
|
+
this.ws.close(1000, 'Client initiated closure');
|
|
293
|
+
}
|
|
294
|
+
else {
|
|
295
|
+
this.ws.terminate();
|
|
296
|
+
}
|
|
263
297
|
}
|
|
264
298
|
}
|
|
265
299
|
cleanupHeartbeat() {
|
|
@@ -269,7 +303,9 @@ class DiscordWebSocket {
|
|
|
269
303
|
}
|
|
270
304
|
}
|
|
271
305
|
shouldReconnect(code) {
|
|
272
|
-
|
|
306
|
+
if (code === 1006)
|
|
307
|
+
return true;
|
|
308
|
+
const fatalErrorCodes = [4004, 4010, 4011, 4013, 4014];
|
|
273
309
|
if (fatalErrorCodes.includes(code)) {
|
|
274
310
|
logger_1.logger.error(`Fatal WebSocket error received (code: ${code}). Will not reconnect.`);
|
|
275
311
|
return false;
|
|
@@ -1,2 +1,13 @@
|
|
|
1
1
|
import { IdentifyPayload } from './types';
|
|
2
|
-
|
|
2
|
+
/**
|
|
3
|
+
* @typedef {object} ClientProperties
|
|
4
|
+
* @property {string} [os] - The operating system. (e.g., 'Windows', 'Android')
|
|
5
|
+
* @property {string} [browser] - The browser or client. (e.g., 'Discord Client', 'Discord Android')
|
|
6
|
+
* @property {string} [device] - The device. (e.g., 'Android16')
|
|
7
|
+
*/
|
|
8
|
+
export interface ClientProperties {
|
|
9
|
+
os?: string;
|
|
10
|
+
browser?: string;
|
|
11
|
+
device?: string;
|
|
12
|
+
}
|
|
13
|
+
export declare function getIdentifyPayload(token: string, properties?: ClientProperties): IdentifyPayload;
|
|
@@ -1,16 +1,17 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.getIdentifyPayload = getIdentifyPayload;
|
|
4
|
-
function getIdentifyPayload(token) {
|
|
4
|
+
function getIdentifyPayload(token, properties) {
|
|
5
|
+
const defaultProperties = {
|
|
6
|
+
os: 'Windows',
|
|
7
|
+
browser: 'Discord Client',
|
|
8
|
+
device: 'hieuxyz©rpc',
|
|
9
|
+
};
|
|
5
10
|
return {
|
|
6
11
|
token: token,
|
|
7
12
|
capabilities: 65,
|
|
8
13
|
largeThreshold: 50,
|
|
9
|
-
properties: {
|
|
10
|
-
os: 'Windows',
|
|
11
|
-
browser: 'Discord Client',
|
|
12
|
-
device: 'hieuxyz©rpc',
|
|
13
|
-
},
|
|
14
|
+
properties: { ...defaultProperties, ...properties },
|
|
14
15
|
compress: true,
|
|
15
16
|
};
|
|
16
17
|
}
|
|
@@ -15,17 +15,100 @@ export interface GatewayPayload {
|
|
|
15
15
|
s?: number | null;
|
|
16
16
|
t?: string | null;
|
|
17
17
|
}
|
|
18
|
+
export interface IdentifyProperties {
|
|
19
|
+
os: string;
|
|
20
|
+
browser: string;
|
|
21
|
+
device: string;
|
|
22
|
+
}
|
|
18
23
|
export interface IdentifyPayload {
|
|
19
24
|
token: string;
|
|
20
25
|
capabilities: number;
|
|
21
26
|
largeThreshold: number;
|
|
22
|
-
properties:
|
|
23
|
-
os: string;
|
|
24
|
-
browser: string;
|
|
25
|
-
device: string;
|
|
26
|
-
};
|
|
27
|
+
properties: IdentifyProperties;
|
|
27
28
|
compress: boolean;
|
|
28
29
|
}
|
|
30
|
+
export declare enum UserFlags {
|
|
31
|
+
STAFF = 1,
|
|
32
|
+
PARTNER = 2,
|
|
33
|
+
HYPESQUAD = 4,
|
|
34
|
+
BUG_HUNTER_LEVEL_1 = 8,
|
|
35
|
+
HYPESQUAD_ONLINE_HOUSE_1 = 64,// Bravery
|
|
36
|
+
HYPESQUAD_ONLINE_HOUSE_2 = 128,// Brilliance
|
|
37
|
+
HYPESQUAD_ONLINE_HOUSE_3 = 256,// Balance
|
|
38
|
+
PREMIUM_EARLY_SUPPORTER = 512,
|
|
39
|
+
TEAM_PSEUDO_USER = 1024,
|
|
40
|
+
BUG_HUNTER_LEVEL_2 = 16384,
|
|
41
|
+
VERIFIED_BOT = 65536,
|
|
42
|
+
VERIFIED_DEVELOPER = 131072,
|
|
43
|
+
CERTIFIED_MODERATOR = 262144,
|
|
44
|
+
BOT_HTTP_INTERACTIONS = 524288,
|
|
45
|
+
ACTIVE_DEVELOPER = 4194304
|
|
46
|
+
}
|
|
47
|
+
export interface DiscordUser {
|
|
48
|
+
id: string;
|
|
49
|
+
username: string;
|
|
50
|
+
discriminator: string;
|
|
51
|
+
global_name?: string | null;
|
|
52
|
+
avatar?: string | null;
|
|
53
|
+
bot?: boolean;
|
|
54
|
+
system?: boolean;
|
|
55
|
+
mfa_enabled?: boolean;
|
|
56
|
+
banner?: string | null;
|
|
57
|
+
accent_color?: number | null;
|
|
58
|
+
locale?: string;
|
|
59
|
+
verified?: boolean;
|
|
60
|
+
email?: string | null;
|
|
61
|
+
flags?: number;
|
|
62
|
+
premium_type?: number;
|
|
63
|
+
public_flags?: number;
|
|
64
|
+
bio?: string;
|
|
65
|
+
phone?: string | null;
|
|
66
|
+
nsfw_allowed?: boolean;
|
|
67
|
+
pronouns?: string;
|
|
68
|
+
mobile?: boolean;
|
|
69
|
+
desktop?: boolean;
|
|
70
|
+
clan?: {
|
|
71
|
+
tag: string;
|
|
72
|
+
identity_guild_id: string;
|
|
73
|
+
badge: string;
|
|
74
|
+
identity_enabled?: boolean;
|
|
75
|
+
} | null;
|
|
76
|
+
primary_guild?: {
|
|
77
|
+
tag: string;
|
|
78
|
+
identity_guild_id: string;
|
|
79
|
+
badge: string;
|
|
80
|
+
identity_enabled?: boolean;
|
|
81
|
+
} | null;
|
|
82
|
+
purchased_flags?: number;
|
|
83
|
+
premium_usage_flags?: number;
|
|
84
|
+
premium?: boolean;
|
|
85
|
+
premium_state?: {
|
|
86
|
+
premium_subscription_type?: number;
|
|
87
|
+
premium_subscription_group_role?: number;
|
|
88
|
+
premium_source?: number;
|
|
89
|
+
} | null;
|
|
90
|
+
avatar_decoration_data?: {
|
|
91
|
+
asset: string;
|
|
92
|
+
sku_id: string;
|
|
93
|
+
expires_at: number | null;
|
|
94
|
+
} | null;
|
|
95
|
+
collectibles?: {
|
|
96
|
+
nameplate?: {
|
|
97
|
+
asset: string;
|
|
98
|
+
label: string;
|
|
99
|
+
sku_id: string;
|
|
100
|
+
palette?: string;
|
|
101
|
+
expires_at?: number | null;
|
|
102
|
+
};
|
|
103
|
+
} | null;
|
|
104
|
+
display_name_styles?: {
|
|
105
|
+
font_id?: number;
|
|
106
|
+
effect_id?: number;
|
|
107
|
+
colors?: number[];
|
|
108
|
+
} | null;
|
|
109
|
+
banner_color?: string | null;
|
|
110
|
+
age_verification_status?: number;
|
|
111
|
+
}
|
|
29
112
|
export interface Activity {
|
|
30
113
|
name: string;
|
|
31
114
|
type: number;
|
|
@@ -34,6 +117,8 @@ export interface Activity {
|
|
|
34
117
|
state?: string;
|
|
35
118
|
platform?: string;
|
|
36
119
|
instance?: boolean;
|
|
120
|
+
flags?: number;
|
|
121
|
+
sync_id?: string;
|
|
37
122
|
party?: {
|
|
38
123
|
id?: string;
|
|
39
124
|
size?: [number, number];
|
|
@@ -48,6 +133,11 @@ export interface Activity {
|
|
|
48
133
|
small_image?: string;
|
|
49
134
|
small_text?: string;
|
|
50
135
|
};
|
|
136
|
+
secrets?: {
|
|
137
|
+
join?: string;
|
|
138
|
+
spectate?: string;
|
|
139
|
+
match?: string;
|
|
140
|
+
};
|
|
51
141
|
buttons?: string[];
|
|
52
142
|
metadata?: {
|
|
53
143
|
button_urls?: string[];
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.ActivityType = void 0;
|
|
3
|
+
exports.UserFlags = exports.ActivityType = void 0;
|
|
4
4
|
var ActivityType;
|
|
5
5
|
(function (ActivityType) {
|
|
6
6
|
ActivityType[ActivityType["Playing"] = 0] = "Playing";
|
|
@@ -10,3 +10,21 @@ var ActivityType;
|
|
|
10
10
|
ActivityType[ActivityType["Custom"] = 4] = "Custom";
|
|
11
11
|
ActivityType[ActivityType["Competing"] = 5] = "Competing";
|
|
12
12
|
})(ActivityType || (exports.ActivityType = ActivityType = {}));
|
|
13
|
+
var UserFlags;
|
|
14
|
+
(function (UserFlags) {
|
|
15
|
+
UserFlags[UserFlags["STAFF"] = 1] = "STAFF";
|
|
16
|
+
UserFlags[UserFlags["PARTNER"] = 2] = "PARTNER";
|
|
17
|
+
UserFlags[UserFlags["HYPESQUAD"] = 4] = "HYPESQUAD";
|
|
18
|
+
UserFlags[UserFlags["BUG_HUNTER_LEVEL_1"] = 8] = "BUG_HUNTER_LEVEL_1";
|
|
19
|
+
UserFlags[UserFlags["HYPESQUAD_ONLINE_HOUSE_1"] = 64] = "HYPESQUAD_ONLINE_HOUSE_1";
|
|
20
|
+
UserFlags[UserFlags["HYPESQUAD_ONLINE_HOUSE_2"] = 128] = "HYPESQUAD_ONLINE_HOUSE_2";
|
|
21
|
+
UserFlags[UserFlags["HYPESQUAD_ONLINE_HOUSE_3"] = 256] = "HYPESQUAD_ONLINE_HOUSE_3";
|
|
22
|
+
UserFlags[UserFlags["PREMIUM_EARLY_SUPPORTER"] = 512] = "PREMIUM_EARLY_SUPPORTER";
|
|
23
|
+
UserFlags[UserFlags["TEAM_PSEUDO_USER"] = 1024] = "TEAM_PSEUDO_USER";
|
|
24
|
+
UserFlags[UserFlags["BUG_HUNTER_LEVEL_2"] = 16384] = "BUG_HUNTER_LEVEL_2";
|
|
25
|
+
UserFlags[UserFlags["VERIFIED_BOT"] = 65536] = "VERIFIED_BOT";
|
|
26
|
+
UserFlags[UserFlags["VERIFIED_DEVELOPER"] = 131072] = "VERIFIED_DEVELOPER";
|
|
27
|
+
UserFlags[UserFlags["CERTIFIED_MODERATOR"] = 262144] = "CERTIFIED_MODERATOR";
|
|
28
|
+
UserFlags[UserFlags["BOT_HTTP_INTERACTIONS"] = 524288] = "BOT_HTTP_INTERACTIONS";
|
|
29
|
+
UserFlags[UserFlags["ACTIVE_DEVELOPER"] = 4194304] = "ACTIVE_DEVELOPER";
|
|
30
|
+
})(UserFlags || (exports.UserFlags = UserFlags = {}));
|
|
@@ -2,10 +2,27 @@ import { DiscordWebSocket } from '../gateway/DiscordWebSocket';
|
|
|
2
2
|
import { SettableActivityType } from '../gateway/entities/types';
|
|
3
3
|
import { ImageService } from './ImageService';
|
|
4
4
|
import { RpcImage } from './RpcImage';
|
|
5
|
+
/**
|
|
6
|
+
* Flags for activities, used with `.setFlags()`.
|
|
7
|
+
* @enum {number}
|
|
8
|
+
*/
|
|
9
|
+
export declare enum ActivityFlags {
|
|
10
|
+
INSTANCE = 1,
|
|
11
|
+
JOIN = 2,
|
|
12
|
+
SPECTATE = 4,
|
|
13
|
+
JOIN_REQUEST = 8,
|
|
14
|
+
SYNC = 16,
|
|
15
|
+
PLAY = 32
|
|
16
|
+
}
|
|
5
17
|
interface RpcButton {
|
|
6
18
|
label: string;
|
|
7
19
|
url: string;
|
|
8
20
|
}
|
|
21
|
+
interface RpcSecrets {
|
|
22
|
+
join?: string;
|
|
23
|
+
spectate?: string;
|
|
24
|
+
match?: string;
|
|
25
|
+
}
|
|
9
26
|
export type DiscordPlatform = 'desktop' | 'android' | 'ios' | 'samsung' | 'xbox' | 'ps4' | 'ps5' | 'embedded';
|
|
10
27
|
/**
|
|
11
28
|
* Class built for creating and managing Discord Rich Presence states.
|
|
@@ -25,90 +42,126 @@ export declare class HieuxyzRPC {
|
|
|
25
42
|
*/
|
|
26
43
|
private resolvedAssetsCache;
|
|
27
44
|
private renewalInterval;
|
|
45
|
+
/**
|
|
46
|
+
* Cache for Application Assets (Bot Assets).
|
|
47
|
+
* Map<ApplicationID, Map<AssetName, AssetID>>
|
|
48
|
+
*/
|
|
49
|
+
private applicationAssetsCache;
|
|
28
50
|
constructor(websocket: DiscordWebSocket, imageService: ImageService);
|
|
51
|
+
/**
|
|
52
|
+
* Returns the URL of the large image asset, if available.
|
|
53
|
+
* @type {string | null}
|
|
54
|
+
* @readonly
|
|
55
|
+
*/
|
|
56
|
+
get largeImageUrl(): string | null;
|
|
57
|
+
/**
|
|
58
|
+
* Returns the URL of the small image asset, if available.
|
|
59
|
+
* @type {string | null}
|
|
60
|
+
* @readonly
|
|
61
|
+
*/
|
|
62
|
+
get smallImageUrl(): string | null;
|
|
63
|
+
private _resolveAssetUrl;
|
|
29
64
|
private _toRpcImage;
|
|
30
65
|
private cleanupNulls;
|
|
31
66
|
private sanitize;
|
|
32
67
|
/**
|
|
33
68
|
* Name the operation (first line of RPC).
|
|
34
|
-
* @param name - Name to display.
|
|
69
|
+
* @param {string} name - Name to display.
|
|
35
70
|
* @returns {this}
|
|
36
71
|
*/
|
|
37
72
|
setName(name: string): this;
|
|
38
73
|
/**
|
|
39
74
|
* Set details for the operation (second line of RPC).
|
|
40
|
-
* @param details - Details to display.
|
|
75
|
+
* @param {string} details - Details to display.
|
|
41
76
|
* @returns {this}
|
|
42
77
|
*/
|
|
43
78
|
setDetails(details: string): this;
|
|
44
79
|
/**
|
|
45
80
|
* Set the state for the operation (third line of the RPC).
|
|
46
|
-
* @param state - State to display.
|
|
81
|
+
* @param {string} state - State to display.
|
|
47
82
|
* @returns {this}
|
|
48
83
|
*/
|
|
49
84
|
setState(state: string): this;
|
|
50
85
|
/**
|
|
51
86
|
* Set the activity type.
|
|
52
|
-
* @param type - The type of activity (e.g. 0, 'playing', or ActivityType.Playing).
|
|
87
|
+
* @param {SettableActivityType} type - The type of activity (e.g. 0, 'playing', or ActivityType.Playing).
|
|
53
88
|
* @returns {this}
|
|
54
89
|
*/
|
|
55
90
|
setType(type: SettableActivityType): this;
|
|
56
91
|
/**
|
|
57
92
|
* Set a start and/or end timestamp for the activity.
|
|
58
|
-
* @param start - Unix timestamp (milliseconds) for start time.
|
|
59
|
-
* @param end - Unix timestamp (milliseconds) for the end time.
|
|
93
|
+
* @param {number} [start] - Unix timestamp (milliseconds) for start time.
|
|
94
|
+
* @param {number} [end] - Unix timestamp (milliseconds) for the end time.
|
|
60
95
|
* @returns {this}
|
|
61
96
|
*/
|
|
62
97
|
setTimestamps(start?: number, end?: number): this;
|
|
63
98
|
/**
|
|
64
99
|
* Set party information for the activity.
|
|
65
|
-
* @param currentSize - Current number of players.
|
|
66
|
-
* @param maxSize - Maximum number of players.
|
|
100
|
+
* @param {number} currentSize - Current number of players.
|
|
101
|
+
* @param {number} maxSize - Maximum number of players.
|
|
67
102
|
* @returns {this}
|
|
68
103
|
*/
|
|
69
104
|
setParty(currentSize: number, maxSize: number): this;
|
|
70
105
|
/**
|
|
71
106
|
* Set large image and its caption text.
|
|
72
|
-
* @param source - Image source (URL, asset key, or RpcImage object).
|
|
73
|
-
* @param text - Text displayed when hovering over image.
|
|
107
|
+
* @param {string | RpcImage} source - Image source (URL, asset key, Asset Name or RpcImage object).
|
|
108
|
+
* @param {string} [text] - Text displayed when hovering over image.
|
|
74
109
|
* @returns {this}
|
|
75
110
|
*/
|
|
76
111
|
setLargeImage(source: string | RpcImage, text?: string): this;
|
|
77
112
|
/**
|
|
78
113
|
* Set the small image and its caption text.
|
|
79
|
-
* @param source - Image source (URL, asset key, or RpcImage object).
|
|
80
|
-
* @param text - Text displayed when hovering over image.
|
|
114
|
+
* @param {string | RpcImage} source - Image source (URL, asset key, Asset Name or RpcImage object).
|
|
115
|
+
* @param {string} [text] - Text displayed when hovering over image.
|
|
81
116
|
* @returns {this}
|
|
82
117
|
*/
|
|
83
118
|
setSmallImage(source: string | RpcImage, text?: string): this;
|
|
84
119
|
/**
|
|
85
120
|
* Set clickable buttons for RPC (up to 2).
|
|
86
|
-
* @param buttons - An array of button objects
|
|
121
|
+
* @param {RpcButton[]} buttons - An array of button objects, each with a `label` and `url`.
|
|
87
122
|
* @returns {this}
|
|
88
123
|
*/
|
|
89
124
|
setButtons(buttons: RpcButton[]): this;
|
|
125
|
+
/**
|
|
126
|
+
* Set secrets for joining, spectating, and matching games.
|
|
127
|
+
* @param {RpcSecrets} secrets - An object with join, spectate, and/or match secrets.
|
|
128
|
+
* @returns {this}
|
|
129
|
+
*/
|
|
130
|
+
setSecrets(secrets: RpcSecrets): this;
|
|
131
|
+
/**
|
|
132
|
+
* Set the sync_id, typically used for Spotify track synchronization.
|
|
133
|
+
* @param {string} syncId - The synchronization ID.
|
|
134
|
+
* @returns {this}
|
|
135
|
+
*/
|
|
136
|
+
setSyncId(syncId: string): this;
|
|
137
|
+
/**
|
|
138
|
+
* Set activity flags. Use the ActivityFlags enum for convenience.
|
|
139
|
+
* @param {number} flags - A number representing the bitwise flags.
|
|
140
|
+
* @returns {this}
|
|
141
|
+
*/
|
|
142
|
+
setFlags(flags: number): this;
|
|
90
143
|
/**
|
|
91
144
|
* Set custom application ID for RPC.
|
|
92
|
-
* @param id - Discord app ID (must be an 18 or 19 digit number string).
|
|
145
|
+
* @param {string} id - Discord app ID (must be an 18 or 19 digit number string).
|
|
93
146
|
* @throws {Error} If ID is invalid.
|
|
94
147
|
* @returns {this}
|
|
95
148
|
*/
|
|
96
149
|
setApplicationId(id: string): this;
|
|
97
150
|
/**
|
|
98
151
|
* Set the user's status (e.g. online, idle, dnd).
|
|
99
|
-
* @param status - Desired state.
|
|
152
|
+
* @param {'online' | 'dnd' | 'idle' | 'invisible' | 'offline'} status - Desired state.
|
|
100
153
|
* @returns {this}
|
|
101
154
|
*/
|
|
102
155
|
setStatus(status: 'online' | 'dnd' | 'idle' | 'invisible' | 'offline'): this;
|
|
103
156
|
/**
|
|
104
157
|
* Set the platform on which the activity is running.
|
|
105
|
-
* @param platform - Platform (e.g. 'desktop', 'xbox').
|
|
158
|
+
* @param {DiscordPlatform} platform - Platform (e.g. 'desktop', 'xbox').
|
|
106
159
|
* @returns {this}
|
|
107
160
|
*/
|
|
108
161
|
setPlatform(platform: DiscordPlatform): this;
|
|
109
162
|
/**
|
|
110
163
|
* Marks the activity as a joinable instance for the game.
|
|
111
|
-
* @param instance - Whether this activity is a specific instance.
|
|
164
|
+
* @param {boolean} instance - Whether this activity is a specific instance.
|
|
112
165
|
* @returns {this}
|
|
113
166
|
*/
|
|
114
167
|
setInstance(instance: boolean): this;
|
|
@@ -117,6 +170,7 @@ export declare class HieuxyzRPC {
|
|
|
117
170
|
clearTimestamps(): this;
|
|
118
171
|
clearParty(): this;
|
|
119
172
|
clearButtons(): this;
|
|
173
|
+
clearSecrets(): this;
|
|
120
174
|
clearInstance(): this;
|
|
121
175
|
clearLargeImage(): this;
|
|
122
176
|
clearSmallImage(): this;
|
|
@@ -127,6 +181,10 @@ export declare class HieuxyzRPC {
|
|
|
127
181
|
* Stops the background process that checks for asset renewal.
|
|
128
182
|
*/
|
|
129
183
|
stopBackgroundRenewal(): void;
|
|
184
|
+
/**
|
|
185
|
+
* Ensure assets are fetched for the current application ID.
|
|
186
|
+
*/
|
|
187
|
+
private ensureAppAssetsLoaded;
|
|
130
188
|
private resolveImage;
|
|
131
189
|
private buildActivity;
|
|
132
190
|
/**
|