alicezetion 1.7.0 → 1.7.2

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 (78) hide show
  1. package/.cache/replit/__replit_disk_meta.json +1 -1
  2. package/.cache/replit/nix/env.json +1 -1
  3. package/Extra/Database/index.js +399 -0
  4. package/Extra/Database/methods.js +286 -0
  5. package/Extra/ExtraAddons.js +213 -0
  6. package/Extra/ExtraGetThread.js +1 -0
  7. package/Extra/ExtraUptimeRobot.js +59 -0
  8. package/Extra/PM2/ecosystem.config.js +23 -0
  9. package/Extra/Src/Last-Run.js +48 -0
  10. package/Language/index.json +151 -0
  11. package/StateCrypt.js +22 -0
  12. package/broadcast.js +42 -0
  13. package/index.js +755 -533
  14. package/logger.js +21 -0
  15. package/package.json +35 -21
  16. package/replit.nix +0 -3
  17. package/src/addExternalModule.js +23 -0
  18. package/{leiamnash → src}/addUserToGroup.js +11 -23
  19. package/{leiamnash → src}/changeAdminStatus.js +32 -16
  20. package/{leiamnash → src}/changeArchivedStatus.js +9 -17
  21. package/src/changeAvt.js +91 -0
  22. package/{leiamnash → src}/changeBio.js +16 -24
  23. package/{leiamnash → src}/changeBlockedStatus.js +13 -18
  24. package/{leiamnash → src}/changeGroupImage.js +14 -23
  25. package/{leiamnash → src}/changeNickname.js +9 -14
  26. package/{leiamnash → src}/changeThreadColor.js +6 -10
  27. package/{leiamnash → src}/changeThreadEmoji.js +6 -11
  28. package/{leiamnash → src}/chat.js +116 -127
  29. package/{leiamnash → src}/createNewGroup.js +19 -27
  30. package/{leiamnash → src}/createPoll.js +6 -12
  31. package/{leiamnash → src}/deleteMessage.js +8 -13
  32. package/{leiamnash → src}/deleteThread.js +7 -14
  33. package/{leiamnash → src}/forwardAttachment.js +9 -16
  34. package/src/getAccessToken.js +32 -0
  35. package/{leiamnash → src}/getCurrentUserID.js +0 -0
  36. package/{leiamnash → src}/getEmojiUrl.js +1 -2
  37. package/{leiamnash → src}/getFriendsList.js +11 -14
  38. package/src/getMessage.js +84 -0
  39. package/{leiamnash → src}/getThreadHistory.js +27 -38
  40. package/{leiamnash → src}/getThreadHistoryDeprecated.js +14 -25
  41. package/src/getThreadInfo.js +197 -0
  42. package/{leiamnash → src}/getThreadInfoDeprecated.js +12 -24
  43. package/{leiamnash → src}/getThreadList.js +122 -88
  44. package/{leiamnash → src}/getThreadListDeprecated.js +9 -20
  45. package/{leiamnash → src}/getThreadPictures.js +9 -17
  46. package/{leiamnash → src}/getUserID.js +8 -11
  47. package/{leiamnash → src}/getUserInfo.js +12 -16
  48. package/src/getUserInfoV2.js +35 -0
  49. package/src/handleFriendRequest.js +47 -0
  50. package/{leiamnash → src}/handleMessageRequest.js +12 -22
  51. package/{leiamnash → src}/httpGet.js +15 -13
  52. package/{leiamnash → src}/httpPost.js +14 -13
  53. package/src/httpPostFormData.js +46 -0
  54. package/src/listenMqtt.js +1280 -0
  55. package/{leiamnash → src}/logout.js +7 -9
  56. package/{leiamnash → src}/markAsDelivered.js +14 -18
  57. package/{leiamnash → src}/markAsRead.js +30 -28
  58. package/{leiamnash → src}/markAsSeen.js +18 -19
  59. package/{leiamnash → src}/muteThread.js +7 -8
  60. package/{leiamnash/setMessageReaction.js → src/react.js} +15 -18
  61. package/{leiamnash → src}/removeUserFromGroup.js +13 -20
  62. package/{leiamnash → src}/resolvePhotoUrl.js +7 -13
  63. package/{leiamnash → src}/searchForThread.js +8 -13
  64. package/{leiamnash/markAsReadAll.js → src/seen.js} +10 -13
  65. package/{leiamnash → src}/sendTypingIndicator.js +23 -31
  66. package/src/setPostReaction.js +104 -0
  67. package/{leiamnash → src}/setTitle.js +15 -21
  68. package/src/threadColors.js +39 -0
  69. package/{leiamnash → src}/unfriend.js +9 -13
  70. package/{leiamnash/unsendMessage.js → src/unsend.js} +7 -16
  71. package/utils.js +1112 -1236
  72. package/leiamnash/addExternalModule.js +0 -19
  73. package/leiamnash/changeApprovalMode.js +0 -80
  74. package/leiamnash/getThreadInfo.js +0 -212
  75. package/leiamnash/handleFriendRequest.js +0 -61
  76. package/leiamnash/listenMqtt.js +0 -1129
  77. package/leiamnash/setPostReaction.js +0 -76
  78. package/leiamnash/threadColors.js +0 -57
@@ -1,1129 +0,0 @@
1
- /* eslint-disable no-redeclare */
2
- "use strict";
3
- var utils = require("../utils");
4
- var log = require("npmlog");
5
- var mqtt = require("mqtt");
6
- var websocket = require("websocket-stream");
7
- var HttpsProxyAgent = require("https-proxy-agent");
8
- const EventEmitter = require("events");
9
-
10
- var identity = function() {};
11
- var form = {};
12
- var getSeqID = function() {};
13
-
14
- var topics = [
15
- "/legacy_web",
16
- "/webrtc",
17
- "/rtc_multi",
18
- "/onevc",
19
- "/br_sr", //Notification
20
- //Need to publish /br_sr right after this
21
- "/sr_res",
22
- "/t_ms",
23
- "/thread_typing",
24
- "/orca_typing_notifications",
25
- "/notify_disconnect",
26
- //Need to publish /messenger_sync_create_queue right after this
27
- "/orca_presence",
28
- //Will receive /sr_res right here.
29
-
30
- "/inbox",
31
- "/mercury",
32
- "/messaging_events",
33
- "/orca_message_notifications",
34
- "/pp",
35
- "/webrtc_response",
36
- ];
37
-
38
- function listenMqtt(defaultFuncs, api, ctx, globalCallback) {
39
- //Don't really know what this does but I think it's for the active state?
40
- //TODO: Move to ctx when implemented
41
- var chatOn = ctx.globalOptions.online;
42
- var foreground = false;
43
-
44
- var sessionID = Math.floor(Math.random() * 9007199254740991) + 1;
45
- var username = {
46
- u: ctx.userID,
47
- s: sessionID,
48
- chat_on: chatOn,
49
- fg: foreground,
50
- d: utils.getGUID(),
51
- ct: "websocket",
52
- //App id from facebook
53
- aid: "219994525426954",
54
- mqtt_sid: "",
55
- cp: 3,
56
- ecp: 10,
57
- st: [],
58
- pm: [],
59
- dc: "",
60
- no_auto_fg: true,
61
- gas: null,
62
- pack: [],
63
- };
64
- var cookies = ctx.jar.getCookies("https://www.facebook.com").join("; ");
65
-
66
- var host;
67
- if (ctx.mqttEndpoint) {
68
- host = `${ctx.mqttEndpoint}&sid=${sessionID}`;
69
- } else if (ctx.region) {
70
- host = `wss://edge-chat.facebook.com/chat?region=${ctx.region.toLocaleLowerCase()}&sid=${sessionID}`;
71
- } else {
72
- host = `wss://edge-chat.facebook.com/chat?sid=${sessionID}`;
73
- }
74
-
75
- var options = {
76
- clientId: "mqttwsclient",
77
- protocolId: "MQIsdp",
78
- protocolVersion: 3,
79
- username: JSON.stringify(username),
80
- clean: true,
81
- wsOptions: {
82
- headers: {
83
- Cookie: cookies,
84
- Origin: "https://www.facebook.com",
85
- "User-Agent": ctx.globalOptions.userAgent,
86
- Referer: "https://www.facebook.com/",
87
- Host: new URL(host).hostname, //'edge-chat.facebook.com'
88
- },
89
- origin: "https://www.facebook.com",
90
- protocolVersion: 13,
91
- },
92
- keepalive: 10,
93
- reschedulePings: false,
94
- };
95
-
96
- if (typeof ctx.globalOptions.proxy != "undefined") {
97
- var agent = new HttpsProxyAgent(ctx.globalOptions.proxy);
98
- options.wsOptions.agent = agent;
99
- }
100
-
101
- ctx.mqttClient = new mqtt.Client(
102
- (_) => websocket(host, options.wsOptions),
103
- options
104
- );
105
-
106
- var mqttClient = ctx.mqttClient;
107
-
108
- mqttClient.on("error", function(err) {
109
- log.error("listenMqtt", err);
110
- mqttClient.end();
111
- if (ctx.globalOptions.autoReconnect) {
112
- getSeqID();
113
- } else {
114
- globalCallback(
115
- {
116
- type: "stop_listen",
117
- error: "Connection refused: Server unavailable",
118
- },
119
- null
120
- );
121
- }
122
- });
123
-
124
- mqttClient.on("connect", function() {
125
- topics.forEach(function(topicsub) {
126
- mqttClient.subscribe(topicsub);
127
- });
128
-
129
- var topic;
130
- var queue = {
131
- sync_api_version: 10,
132
- max_deltas_able_to_process: 1000,
133
- delta_batch_size: 500,
134
- encoding: "JSON",
135
- entity_fbid: ctx.userID,
136
- };
137
-
138
- if (ctx.syncToken) {
139
- topic = "/messenger_sync_get_diffs";
140
- queue.last_seq_id = ctx.lastSeqId;
141
- queue.sync_token = ctx.syncToken;
142
- } else {
143
- topic = "/messenger_sync_create_queue";
144
- queue.initial_titan_sequence_id = ctx.lastSeqId;
145
- queue.device_params = null;
146
- }
147
-
148
- mqttClient.publish(topic, JSON.stringify(queue), {
149
- qos: 1,
150
- retain: false,
151
- });
152
-
153
- var rTimeout = setTimeout(function() {
154
- mqttClient.end();
155
- getSeqID();
156
- }, 5000);
157
-
158
- ctx.tmsWait = function() {
159
- clearTimeout(rTimeout);
160
- ctx.globalOptions.emitReady
161
- ? globalCallback({
162
- type: "ready",
163
- error: null,
164
- })
165
- : "";
166
- delete ctx.tmsWait;
167
- };
168
- });
169
-
170
- mqttClient.on("message", function(topic, message, _packet) {
171
- try {
172
- var jsonMessage = JSON.parse(message);
173
- } catch (ex) {
174
- return log.error("listenMqtt", ex);
175
- }
176
- if (topic === "/t_ms") {
177
- if (ctx.tmsWait && typeof ctx.tmsWait == "function") {
178
- ctx.tmsWait();
179
- }
180
-
181
- if (jsonMessage.firstDeltaSeqId && jsonMessage.syncToken) {
182
- ctx.lastSeqId = jsonMessage.firstDeltaSeqId;
183
- ctx.syncToken = jsonMessage.syncToken;
184
- }
185
-
186
- if (jsonMessage.lastIssuedSeqId) {
187
- ctx.lastSeqId = parseInt(jsonMessage.lastIssuedSeqId);
188
- }
189
-
190
- //If it contains more than 1 delta
191
- for (var i in jsonMessage.deltas) {
192
- var delta = jsonMessage.deltas[i];
193
- parseDelta(defaultFuncs, api, ctx, globalCallback, {
194
- delta: delta,
195
- });
196
- }
197
- } else if (
198
- topic === "/thread_typing" ||
199
- topic === "/orca_typing_notifications"
200
- ) {
201
- var typ = {
202
- type: "typ",
203
- isTyping: !!jsonMessage.state,
204
- from: jsonMessage.sender_fbid.toString(),
205
- threadID: utils.formatID(
206
- (jsonMessage.thread || jsonMessage.sender_fbid).toString()
207
- ),
208
- };
209
- (function() {
210
- globalCallback(null, typ);
211
- })();
212
- } else if (topic === "/orca_presence") {
213
- if (!ctx.globalOptions.updatePresence) {
214
- for (var i in jsonMessage.list) {
215
- var data = jsonMessage.list[i];
216
- var userID = data["u"];
217
-
218
- var presence = {
219
- type: "presence",
220
- userID: userID.toString(),
221
- //Convert to ms
222
- timestamp: data["l"] * 1000,
223
- statuses: data["p"],
224
- };
225
- (function() {
226
- globalCallback(null, presence);
227
- })();
228
- }
229
- }
230
- }
231
- });
232
-
233
- mqttClient.on("close", function() {
234
- //(function () { globalCallback("Connection closed."); })();
235
- // client.end();
236
- });
237
- }
238
-
239
- function parseDelta(defaultFuncs, api, ctx, globalCallback, v) {
240
- if (v.delta.class == "NewMessage") {
241
- //Not tested for pages
242
- if (ctx.globalOptions.pageID && ctx.globalOptions.pageID != v.queue)
243
- return;
244
-
245
- (function resolveAttachmentUrl(i) {
246
- if (v.delta.attachments && i == v.delta.attachments.length) {
247
- var fmtMsg;
248
- try {
249
- fmtMsg = utils.formatDeltaMessage(v);
250
- } catch (err) {
251
- return globalCallback({
252
- error:
253
- "Problem parsing message object. Please open an issue at https://github.com/Schmavery/facebook-chat-api/issues.",
254
- detail: err,
255
- res: v,
256
- type: "parse_error",
257
- });
258
- }
259
- if (fmtMsg) {
260
- if (ctx.globalOptions.autoMarkDelivery) {
261
- markDelivery(
262
- ctx,
263
- api,
264
- fmtMsg.threadID,
265
- fmtMsg.messageID
266
- );
267
- }
268
- }
269
- return !ctx.globalOptions.selfListen &&
270
- fmtMsg.senderID === ctx.userID
271
- ? undefined
272
- : (function() {
273
- globalCallback(null, fmtMsg);
274
- })();
275
- } else {
276
- if (v.delta.attachments[i].mercury.attach_type == "photo") {
277
- api.resolvePhotoUrl(
278
- v.delta.attachments[i].fbid,
279
- (err, url) => {
280
- if (!err)
281
- v.delta.attachments[
282
- i
283
- ].mercury.metadata.url = url;
284
- return resolveAttachmentUrl(i + 1);
285
- }
286
- );
287
- } else {
288
- return resolveAttachmentUrl(i + 1);
289
- }
290
- }
291
- })(0);
292
- }
293
-
294
- if (v.delta.class == "ClientPayload") {
295
- var clientPayload = utils.decodeClientPayload(v.delta.payload);
296
- if (clientPayload && clientPayload.deltas) {
297
- for (var i in clientPayload.deltas) {
298
- var delta = clientPayload.deltas[i];
299
- if (
300
- delta.deltaMessageReaction &&
301
- !!ctx.globalOptions.listenEvents
302
- ) {
303
- (function() {
304
- globalCallback(null, {
305
- type: "message_reaction",
306
- threadID: (delta.deltaMessageReaction.threadKey
307
- .threadFbId
308
- ? delta.deltaMessageReaction.threadKey
309
- .threadFbId
310
- : delta.deltaMessageReaction.threadKey
311
- .otherUserFbId
312
- ).toString(),
313
- messageID: delta.deltaMessageReaction.messageId,
314
- reaction: delta.deltaMessageReaction.reaction,
315
- senderID: delta.deltaMessageReaction.senderId.toString(),
316
- userID: delta.deltaMessageReaction.userId.toString(),
317
- });
318
- })();
319
- } else if (
320
- delta.deltaRecallMessageData &&
321
- !!ctx.globalOptions.listenEvents
322
- ) {
323
- (function() {
324
- globalCallback(null, {
325
- type: "message_unsend",
326
- threadID: (delta.deltaRecallMessageData.threadKey
327
- .threadFbId
328
- ? delta.deltaRecallMessageData.threadKey
329
- .threadFbId
330
- : delta.deltaRecallMessageData.threadKey
331
- .otherUserFbId
332
- ).toString(),
333
- messageID: delta.deltaRecallMessageData.messageID,
334
- senderID: delta.deltaRecallMessageData.senderID.toString(),
335
- deletionTimestamp:
336
- delta.deltaRecallMessageData.deletionTimestamp,
337
- timestamp: delta.deltaRecallMessageData.timestamp,
338
- });
339
- })();
340
- } else if (delta.deltaMessageReply) {
341
- //Mention block - #1
342
- var mdata =
343
- delta.deltaMessageReply.message === undefined
344
- ? []
345
- : delta.deltaMessageReply.message.data === undefined
346
- ? []
347
- : delta.deltaMessageReply.message.data.prng ===
348
- undefined
349
- ? []
350
- : JSON.parse(
351
- delta.deltaMessageReply.message.data.prng
352
- );
353
- var m_id = mdata.map((u) => u.i);
354
- var m_offset = mdata.map((u) => u.o);
355
- var m_length = mdata.map((u) => u.l);
356
-
357
- var mentions = {};
358
-
359
- for (var i = 0; i < m_id.length; i++) {
360
- mentions[m_id[i]] = (
361
- delta.deltaMessageReply.message.body || ""
362
- ).substring(m_offset[i], m_offset[i] + m_length[i]);
363
- }
364
- //Mention block - 1#
365
- var callbackToReturn = {
366
- type: "message_reply",
367
- threadID: (delta.deltaMessageReply.message
368
- .messageMetadata.threadKey.threadFbId
369
- ? delta.deltaMessageReply.message.messageMetadata
370
- .threadKey.threadFbId
371
- : delta.deltaMessageReply.message.messageMetadata
372
- .threadKey.otherUserFbId
373
- ).toString(),
374
- messageID:
375
- delta.deltaMessageReply.message.messageMetadata
376
- .messageId,
377
- senderID: delta.deltaMessageReply.message.messageMetadata.actorFbId.toString(),
378
- attachments: delta.deltaMessageReply.message.attachments
379
- .map(function(att) {
380
- var mercury = JSON.parse(att.mercuryJSON);
381
- Object.assign(att, mercury);
382
- return att;
383
- })
384
- .map((att) => {
385
- var x;
386
- try {
387
- x = utils._formatAttachment(att);
388
- } catch (ex) {
389
- x = att;
390
- x.error = ex;
391
- x.type = "unknown";
392
- }
393
- return x;
394
- }),
395
- args: (delta.deltaMessageReply.message.body || "")
396
- .trim()
397
- .split(/\s+/),
398
- body: delta.deltaMessageReply.message.body || "",
399
- mentions: mentions,
400
- timestamp:
401
- delta.deltaMessageReply.message.messageMetadata
402
- .timestamp,
403
- isGroup: !!delta.deltaMessageReply.message
404
- .messageMetadata.threadKey.threadFbId,
405
- participantIDs: delta.deltaMessageReply.message.participants?.map(
406
- (u) => u.toString()
407
- ),
408
- };
409
-
410
- if (delta.deltaMessageReply.repliedToMessage) {
411
- //Mention block - #2
412
- mdata =
413
- delta.deltaMessageReply.repliedToMessage ===
414
- undefined
415
- ? []
416
- : delta.deltaMessageReply.repliedToMessage
417
- .data === undefined
418
- ? []
419
- : delta.deltaMessageReply.repliedToMessage.data
420
- .prng === undefined
421
- ? []
422
- : JSON.parse(
423
- delta.deltaMessageReply.repliedToMessage
424
- .data.prng
425
- );
426
- m_id = mdata.map((u) => u.i);
427
- m_offset = mdata.map((u) => u.o);
428
- m_length = mdata.map((u) => u.l);
429
-
430
- var rmentions = {};
431
-
432
- for (var i = 0; i < m_id.length; i++) {
433
- rmentions[m_id[i]] = (
434
- delta.deltaMessageReply.repliedToMessage.body ||
435
- ""
436
- ).substring(m_offset[i], m_offset[i] + m_length[i]);
437
- }
438
- //Mention block - 2#
439
- callbackToReturn.messageReply = {
440
- threadID: (delta.deltaMessageReply.repliedToMessage
441
- .messageMetadata.threadKey.threadFbId
442
- ? delta.deltaMessageReply.repliedToMessage
443
- .messageMetadata.threadKey.threadFbId
444
- : delta.deltaMessageReply.repliedToMessage
445
- .messageMetadata.threadKey.otherUserFbId
446
- ).toString(),
447
- messageID:
448
- delta.deltaMessageReply.repliedToMessage
449
- .messageMetadata.messageId,
450
- senderID: delta.deltaMessageReply.repliedToMessage.messageMetadata.actorFbId.toString(),
451
- attachments: delta.deltaMessageReply.repliedToMessage.attachments
452
- .map(function(att) {
453
- var mercury = JSON.parse(att.mercuryJSON);
454
- Object.assign(att, mercury);
455
- return att;
456
- })
457
- .map((att) => {
458
- var x;
459
- try {
460
- x = utils._formatAttachment(att);
461
- } catch (ex) {
462
- x = att;
463
- x.error = ex;
464
- x.type = "unknown";
465
- }
466
- return x;
467
- }),
468
- args: (
469
- delta.deltaMessageReply.repliedToMessage.body ||
470
- ""
471
- )
472
- .trim()
473
- .split(/\s+/),
474
- body:
475
- delta.deltaMessageReply.repliedToMessage.body ||
476
- "",
477
- isGroup: !!delta.deltaMessageReply.repliedToMessage
478
- .messageMetadata.threadKey.threadFbId,
479
- mentions: rmentions,
480
- timestamp:
481
- delta.deltaMessageReply.repliedToMessage
482
- .messageMetadata.timestamp,
483
- };
484
- } else if (delta.deltaMessageReply.replyToMessageId) {
485
- return defaultFuncs
486
- .post(
487
- "https://www.facebook.com/api/graphqlbatch/",
488
- ctx.jar,
489
- {
490
- av: ctx.globalOptions.pageID,
491
- queries: JSON.stringify({
492
- o0: {
493
- //Using the same doc_id as forcedFetch
494
- doc_id: "2848441488556444",
495
- query_params: {
496
- thread_and_message_id: {
497
- thread_id:
498
- callbackToReturn.threadID,
499
- message_id:
500
- delta.deltaMessageReply
501
- .replyToMessageId
502
- .id,
503
- },
504
- },
505
- },
506
- }),
507
- }
508
- )
509
- .then(utils.parseAndCheckLogin(ctx, defaultFuncs))
510
- .then((resData) => {
511
- if (
512
- resData[resData.length - 1].error_results >
513
- 0
514
- ) {
515
- throw resData[0].o0.errors;
516
- }
517
-
518
- if (
519
- resData[resData.length - 1]
520
- .successful_results === 0
521
- ) {
522
- throw {
523
- error:
524
- "forcedFetch: there was no successful_results",
525
- res: resData,
526
- };
527
- }
528
-
529
- var fetchData = resData[0].o0.data.message;
530
-
531
- var mobj = {};
532
- for (var n in fetchData.message.ranges) {
533
- mobj[
534
- fetchData.message.ranges[n].entity.id
535
- ] = (fetchData.message.text || "").substr(
536
- fetchData.message.ranges[n].offset,
537
- fetchData.message.ranges[n].length
538
- );
539
- }
540
-
541
- callbackToReturn.messageReply = {
542
- threadID: callbackToReturn.threadID,
543
- messageID: fetchData.message_id,
544
- senderID: fetchData.message_sender.id.toString(),
545
- attachments: fetchData.message.blob_attachment.map(
546
- (att) => {
547
- var x;
548
- try {
549
- x = utils._formatAttachment({
550
- blob_attachment: att,
551
- });
552
- } catch (ex) {
553
- x = att;
554
- x.error = ex;
555
- x.type = "unknown";
556
- }
557
- return x;
558
- }
559
- ),
560
- args: (
561
- delta.deltaMessageReply.repliedToMessage
562
- .body || ""
563
- )
564
- .trim()
565
- .split(/\s+/),
566
- body: fetchData.message.text || "",
567
- isGroup: callbackToReturn.isGroup,
568
- mentions: mobj,
569
- timestamp: parseInt(
570
- fetchData.timestamp_precise
571
- ),
572
- };
573
- })
574
- .catch((err) => {
575
- log.error("forcedFetch", err);
576
- })
577
- .finally(function() {
578
- if (ctx.globalOptions.autoMarkDelivery) {
579
- markDelivery(
580
- ctx,
581
- api,
582
- callbackToReturn.threadID,
583
- callbackToReturn.messageID
584
- );
585
- }
586
- !ctx.globalOptions.selfListen &&
587
- callbackToReturn.senderID === ctx.userID
588
- ? undefined
589
- : (function() {
590
- globalCallback(
591
- null,
592
- callbackToReturn
593
- );
594
- })();
595
- });
596
- } else {
597
- callbackToReturn.delta = delta;
598
- }
599
-
600
- if (ctx.globalOptions.autoMarkDelivery) {
601
- markDelivery(
602
- ctx,
603
- api,
604
- callbackToReturn.threadID,
605
- callbackToReturn.messageID
606
- );
607
- }
608
-
609
- return !ctx.globalOptions.selfListen &&
610
- callbackToReturn.senderID === ctx.userID
611
- ? undefined
612
- : (function() {
613
- globalCallback(null, callbackToReturn);
614
- })();
615
- }
616
- }
617
- return;
618
- }
619
- }
620
-
621
- if (v.delta.class !== "NewMessage" && !ctx.globalOptions.listenEvents)
622
- return;
623
-
624
- switch (v.delta.class) {
625
- case "ReadReceipt":
626
- var fmtMsg;
627
- try {
628
- fmtMsg = utils.formatDeltaReadReceipt(v.delta);
629
- } catch (err) {
630
- return globalCallback({
631
- error:
632
- "Problem parsing message object. Please open an issue at https://github.com/Schmavery/facebook-chat-api/issues.",
633
- detail: err,
634
- res: v.delta,
635
- type: "parse_error",
636
- });
637
- }
638
- return (function() {
639
- globalCallback(null, fmtMsg);
640
- })();
641
- case "AdminTextMessage":
642
- switch (v.delta.type) {
643
- case "change_thread_theme":
644
- // case "change_thread_icon": deprecated
645
- case "change_thread_quick_reaction":
646
- case "change_thread_nickname":
647
- case "change_thread_admins":
648
- case "change_thread_approval_mode":
649
- case "group_poll":
650
- case "messenger_call_log":
651
- case "participant_joined_group_call":
652
- var fmtMsg;
653
- try {
654
- fmtMsg = utils.formatDeltaEvent(v.delta);
655
- } catch (err) {
656
- return globalCallback({
657
- error:
658
- "Problem parsing message object. Please open an issue at https://github.com/Schmavery/facebook-chat-api/issues.",
659
- detail: err,
660
- res: v.delta,
661
- type: "parse_error",
662
- });
663
- }
664
- return (function() {
665
- globalCallback(null, fmtMsg);
666
- })();
667
- default:
668
- return;
669
- }
670
- break;
671
- //For group images
672
- case "ForcedFetch":
673
- if (!v.delta.threadKey) return;
674
- var mid = v.delta.messageId;
675
- var tid = v.delta.threadKey.threadFbId;
676
- if (mid && tid) {
677
- const form = {
678
- av: ctx.globalOptions.pageID,
679
- queries: JSON.stringify({
680
- o0: {
681
- //This doc_id is valid as of March 25, 2020
682
- doc_id: "2848441488556444",
683
- query_params: {
684
- thread_and_message_id: {
685
- thread_id: tid.toString(),
686
- message_id: mid,
687
- },
688
- },
689
- },
690
- }),
691
- };
692
-
693
- defaultFuncs
694
- .post(
695
- "https://www.facebook.com/api/graphqlbatch/",
696
- ctx.jar,
697
- form
698
- )
699
- .then(utils.parseAndCheckLogin(ctx, defaultFuncs))
700
- .then((resData) => {
701
- if (resData[resData.length - 1].error_results > 0) {
702
- throw resData[0].o0.errors;
703
- }
704
-
705
- if (
706
- resData[resData.length - 1].successful_results === 0
707
- ) {
708
- throw {
709
- error:
710
- "forcedFetch: there was no successful_results",
711
- res: resData,
712
- };
713
- }
714
-
715
- var fetchData = resData[0].o0.data.message;
716
-
717
- if (utils.getType(fetchData) == "Object") {
718
- log.info("forcedFetch", fetchData);
719
- switch (fetchData.__typename) {
720
- case "ThreadImageMessage":
721
- (!ctx.globalOptions.selfListen &&
722
- fetchData.message_sender.id.toString() ===
723
- ctx.userID) ||
724
- !ctx.loggedIn
725
- ? undefined
726
- : (function() {
727
- globalCallback(null, {
728
- type: "event",
729
- threadID: utils.formatID(
730
- tid.toString()
731
- ),
732
- logMessageType:
733
- "log:thread-image",
734
- logMessageData: {
735
- image: {
736
- attachmentID:
737
- fetchData.image_with_metadata &&
738
- fetchData
739
- .image_with_metadata
740
- .legacy_attachment_id,
741
- width:
742
- fetchData.image_with_metadata &&
743
- fetchData
744
- .image_with_metadata
745
- .original_dimensions
746
- .x,
747
- height:
748
- fetchData.image_with_metadata &&
749
- fetchData
750
- .image_with_metadata
751
- .original_dimensions
752
- .y,
753
- url:
754
- fetchData.image_with_metadata &&
755
- fetchData
756
- .image_with_metadata
757
- .preview.uri,
758
- },
759
- },
760
- logMessageBody:
761
- fetchData.snippet,
762
- timestamp:
763
- fetchData.timestamp_precise,
764
- author:
765
- fetchData.message_sender
766
- .id,
767
- });
768
- })();
769
- break;
770
- case "UserMessage":
771
- log.info("ff-Return", {
772
- type: "message",
773
- senderID: utils.formatID(
774
- fetchData.message_sender.id
775
- ),
776
- body: fetchData.message.text || "",
777
- threadID: utils.formatID(
778
- tid.toString()
779
- ),
780
- messageID: fetchData.message_id,
781
- attachments: [
782
- {
783
- type: "share",
784
- ID:
785
- fetchData
786
- .extensible_attachment
787
- .legacy_attachment_id,
788
- url:
789
- fetchData
790
- .extensible_attachment
791
- .story_attachment.url,
792
-
793
- title:
794
- fetchData
795
- .extensible_attachment
796
- .story_attachment
797
- .title_with_entities
798
- .text,
799
- description:
800
- fetchData
801
- .extensible_attachment
802
- .story_attachment
803
- .description.text,
804
- source:
805
- fetchData
806
- .extensible_attachment
807
- .story_attachment
808
- .source,
809
-
810
- image: (
811
- (
812
- fetchData
813
- .extensible_attachment
814
- .story_attachment
815
- .media || {}
816
- ).image || {}
817
- ).uri,
818
- width: (
819
- (
820
- fetchData
821
- .extensible_attachment
822
- .story_attachment
823
- .media || {}
824
- ).image || {}
825
- ).width,
826
- height: (
827
- (
828
- fetchData
829
- .extensible_attachment
830
- .story_attachment
831
- .media || {}
832
- ).image || {}
833
- ).height,
834
- playable:
835
- (
836
- fetchData
837
- .extensible_attachment
838
- .story_attachment
839
- .media || {}
840
- ).is_playable || false,
841
- duration:
842
- (
843
- fetchData
844
- .extensible_attachment
845
- .story_attachment
846
- .media || {}
847
- ).playable_duration_in_ms ||
848
- 0,
849
-
850
- subattachments:
851
- fetchData
852
- .extensible_attachment
853
- .subattachments,
854
- properties:
855
- fetchData
856
- .extensible_attachment
857
- .story_attachment
858
- .properties,
859
- },
860
- ],
861
- mentions: {},
862
- timestamp: parseInt(
863
- fetchData.timestamp_precise
864
- ),
865
- isGroup:
866
- fetchData.message_sender.id !=
867
- tid.toString(),
868
- });
869
- globalCallback(null, {
870
- type: "message",
871
- senderID: utils.formatID(
872
- fetchData.message_sender.id
873
- ),
874
- body: fetchData.message.text || "",
875
- threadID: utils.formatID(
876
- tid.toString()
877
- ),
878
- messageID: fetchData.message_id,
879
- attachments: [
880
- {
881
- type: "share",
882
- ID:
883
- fetchData
884
- .extensible_attachment
885
- .legacy_attachment_id,
886
- url:
887
- fetchData
888
- .extensible_attachment
889
- .story_attachment.url,
890
-
891
- title:
892
- fetchData
893
- .extensible_attachment
894
- .story_attachment
895
- .title_with_entities
896
- .text,
897
- description:
898
- fetchData
899
- .extensible_attachment
900
- .story_attachment
901
- .description.text,
902
- source:
903
- fetchData
904
- .extensible_attachment
905
- .story_attachment
906
- .source,
907
-
908
- image: (
909
- (
910
- fetchData
911
- .extensible_attachment
912
- .story_attachment
913
- .media || {}
914
- ).image || {}
915
- ).uri,
916
- width: (
917
- (
918
- fetchData
919
- .extensible_attachment
920
- .story_attachment
921
- .media || {}
922
- ).image || {}
923
- ).width,
924
- height: (
925
- (
926
- fetchData
927
- .extensible_attachment
928
- .story_attachment
929
- .media || {}
930
- ).image || {}
931
- ).height,
932
- playable:
933
- (
934
- fetchData
935
- .extensible_attachment
936
- .story_attachment
937
- .media || {}
938
- ).is_playable || false,
939
- duration:
940
- (
941
- fetchData
942
- .extensible_attachment
943
- .story_attachment
944
- .media || {}
945
- ).playable_duration_in_ms ||
946
- 0,
947
-
948
- subattachments:
949
- fetchData
950
- .extensible_attachment
951
- .subattachments,
952
- properties:
953
- fetchData
954
- .extensible_attachment
955
- .story_attachment
956
- .properties,
957
- },
958
- ],
959
- mentions: {},
960
- timestamp: parseInt(
961
- fetchData.timestamp_precise
962
- ),
963
- isGroup:
964
- fetchData.message_sender.id !=
965
- tid.toString(),
966
- });
967
- }
968
- } else {
969
- log.error("forcedFetch", fetchData);
970
- }
971
- })
972
- .catch((err) => {
973
- log.error("forcedFetch", err);
974
- });
975
- }
976
- break;
977
- case "ThreadName":
978
- case "ParticipantsAddedToGroupThread":
979
- case "ParticipantLeftGroupThread":
980
- var formattedEvent;
981
- try {
982
- formattedEvent = utils.formatDeltaEvent(v.delta);
983
- } catch (err) {
984
- return globalCallback({
985
- error:
986
- "Problem parsing message object. Please open an issue at https://github.com/Schmavery/facebook-chat-api/issues.",
987
- detail: err,
988
- res: v.delta,
989
- type: "parse_error",
990
- });
991
- }
992
- return (!ctx.globalOptions.selfListen &&
993
- formattedEvent.author.toString() === ctx.userID) ||
994
- !ctx.loggedIn
995
- ? undefined
996
- : (function() {
997
- globalCallback(null, formattedEvent);
998
- })();
999
- }
1000
- }
1001
-
1002
- function markDelivery(ctx, api, threadID, messageID) {
1003
- if (threadID && messageID) {
1004
- api.markAsDelivered(threadID, messageID, (err) => {
1005
- if (err) {
1006
- log.error("markAsDelivered", err);
1007
- } else {
1008
- if (ctx.globalOptions.autoMarkRead) {
1009
- api.markAsRead(threadID, (err) => {
1010
- if (err) {
1011
- log.error("markAsDelivered", err);
1012
- }
1013
- });
1014
- }
1015
- }
1016
- });
1017
- }
1018
- }
1019
-
1020
- module.exports = function(defaultFuncs, api, ctx) {
1021
- var globalCallback = identity;
1022
- getSeqID = function getSeqID() {
1023
- ctx.t_mqttCalled = false;
1024
- defaultFuncs
1025
- .post("https://www.facebook.com/api/graphqlbatch/", ctx.jar, form)
1026
- .then(utils.parseAndCheckLogin(ctx, defaultFuncs))
1027
- .then((resData) => {
1028
- if (utils.getType(resData) != "Array") {
1029
- throw {
1030
- error: "Not logged in",
1031
- res: resData,
1032
- };
1033
- }
1034
-
1035
- if (resData && resData[resData.length - 1].error_results > 0) {
1036
- throw resData[0].o0.errors;
1037
- }
1038
-
1039
- if (resData[resData.length - 1].successful_results === 0) {
1040
- throw {
1041
- error: "getSeqId: there was no successful_results",
1042
- res: resData,
1043
- };
1044
- }
1045
-
1046
- if (
1047
- resData[0].o0.data.viewer.message_threads.sync_sequence_id
1048
- ) {
1049
- ctx.lastSeqId =
1050
- resData[0].o0.data.viewer.message_threads.sync_sequence_id;
1051
- listenMqtt(defaultFuncs, api, ctx, globalCallback);
1052
- } else {
1053
- throw {
1054
- error: "getSeqId: no sync_sequence_id found.",
1055
- res: resData,
1056
- };
1057
- }
1058
- })
1059
- .catch((err) => {
1060
- log.error("getSeqId", err);
1061
- if (
1062
- utils.getType(err) == "Object" &&
1063
- err.error === "Not logged in"
1064
- ) {
1065
- ctx.loggedIn = false;
1066
- }
1067
- return globalCallback(err);
1068
- });
1069
- };
1070
-
1071
- return function(callback) {
1072
- class MessageEmitter extends EventEmitter {
1073
- stopListening(callback) {
1074
- callback = callback || (() => {});
1075
- globalCallback = identity;
1076
- if (ctx.mqttClient) {
1077
- ctx.mqttClient.unsubscribe("/webrtc");
1078
- ctx.mqttClient.unsubscribe("/rtc_multi");
1079
- ctx.mqttClient.unsubscribe("/onevc");
1080
- ctx.mqttClient.publish("/browser_close", "{}");
1081
- ctx.mqttClient.end(false, function(...data) {
1082
- callback(data);
1083
- ctx.mqttClient = undefined;
1084
- });
1085
- }
1086
- }
1087
- }
1088
-
1089
- var msgEmitter = new MessageEmitter();
1090
- globalCallback =
1091
- callback ||
1092
- function(error, message) {
1093
- if (error) {
1094
- return msgEmitter.emit("error", error);
1095
- }
1096
- msgEmitter.emit("message", message);
1097
- };
1098
-
1099
- //Reset some stuff
1100
- if (!ctx.firstListen) ctx.lastSeqId = null;
1101
- ctx.syncToken = undefined;
1102
- ctx.t_mqttCalled = false;
1103
-
1104
- //Same request as getThreadList
1105
- form = {
1106
- av: ctx.globalOptions.pageID,
1107
- queries: JSON.stringify({
1108
- o0: {
1109
- doc_id: "3336396659757871",
1110
- query_params: {
1111
- limit: 1,
1112
- before: null,
1113
- tags: ["INBOX"],
1114
- includeDeliveryReceipts: false,
1115
- includeSeqID: true,
1116
- },
1117
- },
1118
- }),
1119
- };
1120
-
1121
- if (!ctx.firstListen || !ctx.lastSeqId) {
1122
- getSeqID();
1123
- } else {
1124
- listenMqtt(defaultFuncs, api, ctx, globalCallback);
1125
- }
1126
- ctx.firstListen = false;
1127
- return msgEmitter;
1128
- };
1129
- };