@hbmodsofc/baileys 1.7.8 → 2.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.
Files changed (155) hide show
  1. package/LICENSE +1 -1
  2. package/lib/Defaults/baileys-version.json +3 -0
  3. package/lib/Defaults/index.d.ts +8 -12
  4. package/lib/Defaults/index.js +124 -90
  5. package/lib/Defaults/phonenumber-mcc.json +223 -0
  6. package/lib/Signal/Group/group_cipher.d.ts +1 -0
  7. package/lib/Signal/Group/group_cipher.js +39 -28
  8. package/lib/Signal/Group/queue-job.d.ts +1 -0
  9. package/lib/Signal/Group/queue-job.js +57 -0
  10. package/lib/Signal/Group/sender-chain-key.d.ts +1 -1
  11. package/lib/Signal/Group/sender-chain-key.js +2 -9
  12. package/lib/Signal/Group/sender-key-distribution-message.js +3 -3
  13. package/lib/Signal/Group/sender-key-message.js +3 -3
  14. package/lib/Signal/Group/sender-key-state.d.ts +4 -4
  15. package/lib/Signal/Group/sender-key-state.js +16 -47
  16. package/lib/Signal/libsignal.d.ts +3 -7
  17. package/lib/Signal/libsignal.js +39 -224
  18. package/lib/Socket/Client/{types.d.ts → abstract-socket-client.d.ts} +3 -1
  19. package/lib/Socket/Client/index.d.ts +3 -2
  20. package/lib/Socket/Client/index.js +3 -2
  21. package/lib/Socket/Client/mobile-socket-client.d.ts +13 -0
  22. package/lib/Socket/Client/mobile-socket-client.js +65 -0
  23. package/lib/Socket/Client/{websocket.d.ts → web-socket-client.d.ts} +1 -1
  24. package/lib/Socket/Client/{websocket.js → web-socket-client.js} +16 -10
  25. package/lib/Socket/business.d.ts +78 -94
  26. package/lib/Socket/business.js +11 -130
  27. package/lib/Socket/chats.d.ts +233 -63
  28. package/lib/Socket/chats.js +184 -234
  29. package/lib/Socket/groups.d.ts +41 -62
  30. package/lib/Socket/groups.js +64 -76
  31. package/lib/Socket/hbmods.d.ts +253 -0
  32. package/lib/Socket/hbmods.js +1 -0
  33. package/lib/Socket/index.d.ts +83 -129
  34. package/lib/Socket/index.js +6 -13
  35. package/lib/Socket/messages-recv.d.ts +48 -59
  36. package/lib/Socket/messages-recv.js +371 -516
  37. package/lib/Socket/messages-send.d.ts +67 -86
  38. package/lib/Socket/messages-send.js +1 -1091
  39. package/lib/Socket/newsletter.d.ts +64 -76
  40. package/lib/Socket/newsletter.js +1 -184
  41. package/lib/Socket/registration.d.ts +267 -0
  42. package/lib/Socket/registration.js +166 -0
  43. package/lib/Socket/socket.d.ts +13 -19
  44. package/lib/Socket/socket.js +1 -805
  45. package/lib/Socket/usync.d.ts +36 -0
  46. package/lib/Socket/usync.js +70 -0
  47. package/lib/Types/Auth.d.ts +10 -4
  48. package/lib/Types/Call.d.ts +1 -1
  49. package/lib/Types/Chat.d.ts +9 -29
  50. package/lib/Types/Chat.js +1 -7
  51. package/lib/Types/Contact.d.ts +1 -5
  52. package/lib/Types/Events.d.ts +14 -55
  53. package/lib/Types/GroupMetadata.d.ts +5 -15
  54. package/lib/Types/Label.d.ts +0 -11
  55. package/lib/Types/Label.js +1 -1
  56. package/lib/Types/LabelAssociation.js +1 -1
  57. package/lib/Types/Message.d.ts +49 -75
  58. package/lib/Types/Message.js +7 -10
  59. package/lib/Types/Newsletter.d.ts +98 -129
  60. package/lib/Types/Newsletter.js +38 -33
  61. package/lib/Types/Product.d.ts +1 -1
  62. package/lib/Types/Signal.d.ts +1 -29
  63. package/lib/Types/Socket.d.ts +22 -48
  64. package/lib/Types/State.d.ts +2 -13
  65. package/lib/Types/State.js +0 -12
  66. package/lib/Types/USync.d.ts +1 -1
  67. package/lib/Types/index.d.ts +3 -10
  68. package/lib/Types/index.js +2 -2
  69. package/lib/Utils/auth-utils.d.ts +3 -3
  70. package/lib/Utils/auth-utils.js +102 -378
  71. package/lib/Utils/baileys-event-stream.js +1 -1
  72. package/lib/Utils/business.d.ts +2 -2
  73. package/lib/Utils/business.js +13 -19
  74. package/lib/Utils/chat-utils.d.ts +22 -21
  75. package/lib/Utils/chat-utils.js +154 -201
  76. package/lib/Utils/crypto.d.ts +19 -18
  77. package/lib/Utils/crypto.js +37 -78
  78. package/lib/Utils/decode-wa-message.d.ts +7 -34
  79. package/lib/Utils/decode-wa-message.js +66 -138
  80. package/lib/Utils/event-buffer.d.ts +8 -6
  81. package/lib/Utils/event-buffer.js +43 -81
  82. package/lib/Utils/generics.d.ts +27 -27
  83. package/lib/Utils/generics.js +133 -128
  84. package/lib/Utils/history.d.ts +5 -9
  85. package/lib/Utils/history.js +23 -17
  86. package/lib/Utils/index.d.ts +0 -2
  87. package/lib/Utils/index.js +0 -2
  88. package/lib/Utils/link-preview.d.ts +4 -4
  89. package/lib/Utils/link-preview.js +12 -40
  90. package/lib/Utils/logger.d.ts +3 -11
  91. package/lib/Utils/lt-hash.d.ts +8 -8
  92. package/lib/Utils/lt-hash.js +24 -23
  93. package/lib/Utils/make-mutex.d.ts +2 -2
  94. package/lib/Utils/make-mutex.js +2 -3
  95. package/lib/Utils/messages-media.d.ts +41 -37
  96. package/lib/Utils/messages-media.js +368 -252
  97. package/lib/Utils/messages.d.ts +15 -13
  98. package/lib/Utils/messages.js +261 -274
  99. package/lib/Utils/noise-handler.d.ts +15 -13
  100. package/lib/Utils/noise-handler.js +26 -20
  101. package/lib/Utils/process-message.d.ts +8 -9
  102. package/lib/Utils/process-message.js +93 -157
  103. package/lib/Utils/signal.d.ts +5 -6
  104. package/lib/Utils/signal.js +29 -37
  105. package/lib/Utils/use-multi-file-auth-state.d.ts +2 -1
  106. package/lib/Utils/use-multi-file-auth-state.js +7 -12
  107. package/lib/Utils/validate-connection.d.ts +6 -5
  108. package/lib/Utils/validate-connection.js +97 -39
  109. package/lib/WABinary/constants.d.ts +27 -24
  110. package/lib/WABinary/constants.js +13 -1276
  111. package/lib/WABinary/decode.d.ts +4 -3
  112. package/lib/WABinary/decode.js +14 -28
  113. package/lib/WABinary/encode.d.ts +2 -1
  114. package/lib/WABinary/encode.js +147 -134
  115. package/lib/WABinary/generic-utils.d.ts +7 -4
  116. package/lib/WABinary/generic-utils.js +125 -40
  117. package/lib/WABinary/jid-utils.d.ts +8 -13
  118. package/lib/WABinary/jid-utils.js +16 -27
  119. package/lib/WAM/BinaryInfo.d.ts +11 -2
  120. package/lib/WAM/constants.d.ts +2 -3
  121. package/lib/WAM/constants.js +2359 -2252
  122. package/lib/WAM/encode.d.ts +2 -1
  123. package/lib/WAM/encode.js +11 -8
  124. package/lib/WAUSync/Protocols/USyncContactProtocol.d.ts +2 -2
  125. package/lib/WAUSync/Protocols/USyncContactProtocol.js +4 -3
  126. package/lib/WAUSync/Protocols/USyncDeviceProtocol.d.ts +2 -2
  127. package/lib/WAUSync/Protocols/USyncDeviceProtocol.js +5 -5
  128. package/lib/WAUSync/Protocols/USyncDisappearingModeProtocol.d.ts +2 -2
  129. package/lib/WAUSync/Protocols/USyncDisappearingModeProtocol.js +5 -5
  130. package/lib/WAUSync/Protocols/USyncStatusProtocol.d.ts +2 -2
  131. package/lib/WAUSync/Protocols/USyncStatusProtocol.js +6 -5
  132. package/lib/WAUSync/Protocols/UsyncBotProfileProtocol.d.ts +2 -2
  133. package/lib/WAUSync/Protocols/UsyncBotProfileProtocol.js +1 -1
  134. package/lib/WAUSync/Protocols/UsyncLIDProtocol.d.ts +3 -4
  135. package/lib/WAUSync/Protocols/UsyncLIDProtocol.js +3 -11
  136. package/lib/WAUSync/USyncQuery.d.ts +2 -2
  137. package/lib/WAUSync/USyncQuery.js +15 -19
  138. package/lib/WAUSync/USyncUser.d.ts +5 -5
  139. package/lib/WAUSync/index.d.ts +1 -1
  140. package/lib/WAUSync/index.js +1 -1
  141. package/package.json +102 -104
  142. package/WAProto/index.js +0 -37306
  143. package/lib/Signal/lid-mapping.d.ts +0 -26
  144. package/lib/Signal/lid-mapping.js +0 -146
  145. package/lib/Socket/communities.d.ts +0 -232
  146. package/lib/Socket/communities.js +0 -402
  147. package/lib/Socket/mex.d.ts +0 -2
  148. package/lib/Socket/mex.js +0 -45
  149. package/lib/Types/Bussines.d.ts +0 -24
  150. package/lib/Types/Bussines.js +0 -2
  151. package/lib/Utils/lidToJid-test.d.ts +0 -11
  152. package/lib/Utils/lidToJid-test.js +0 -27
  153. package/lib/Utils/message-retry-manager.d.ts +0 -81
  154. package/lib/Utils/message-retry-manager.js +0 -152
  155. /package/lib/Socket/Client/{types.js → abstract-socket-client.js} +0 -0
@@ -1,15 +1,14 @@
1
- "use strict";
1
+ "use strict";
2
2
  var __importDefault = (this && this.__importDefault) || function (mod) {
3
3
  return (mod && mod.__esModule) ? mod : { "default": mod };
4
4
  };
5
5
  Object.defineProperty(exports, "__esModule", { value: true });
6
- exports.assertMediaContent = exports.downloadMediaMessage = exports.aggregateMessageKeysNotFromMe = exports.updateMessageWithPollUpdate = exports.updateMessageWithReaction = exports.updateMessageWithReceipt = exports.getDevice = exports.extractMessageContent = exports.normalizeMessageContent = exports.getContentType = exports.generateWAMessage = exports.generateWAMessageFromContent = exports.generateWAMessageContent = exports.generateForwardMessageContent = exports.prepareDisappearingMessageSettingContent = exports.prepareWAMessageMedia = exports.generateLinkPreviewIfRequired = exports.extractUrlFromText = void 0;
7
- exports.getAggregateVotesInPollMessage = getAggregateVotesInPollMessage;
6
+ exports.assertMediaContent = exports.downloadMediaMessage = exports.aggregateMessageKeysNotFromMe = exports.getAggregateVotesInPollMessage = exports.updateMessageWithPollUpdate = exports.updateMessageWithReaction = exports.updateMessageWithReceipt = exports.getDevice = exports.extractMessageContent = exports.normalizeMessageContent = exports.getContentType = exports.generateWAMessage = exports.generateWAMessageFromContent = exports.generateWAMessageContent = exports.generateForwardMessageContent = exports.prepareDisappearingMessageSettingContent = exports.prepareWAMessageMedia = exports.generateLinkPreviewIfRequired = exports.extractUrlFromText = void 0;
8
7
  const boom_1 = require("@hapi/boom");
9
8
  const axios_1 = __importDefault(require("axios"));
10
9
  const crypto_1 = require("crypto");
11
10
  const fs_1 = require("fs");
12
- const index_js_1 = require("../../WAProto/index.js");
11
+ const WAProto_1 = require("../../WAProto");
13
12
  const Defaults_1 = require("../Defaults");
14
13
  const Types_1 = require("../Types");
15
14
  const WABinary_1 = require("../WABinary");
@@ -22,21 +21,22 @@ const MIMETYPE_MAP = {
22
21
  document: 'application/pdf',
23
22
  audio: 'audio/ogg; codecs=opus',
24
23
  sticker: 'image/webp',
25
- 'product-catalog-image': 'image/jpeg'
24
+ 'product-catalog-image': 'image/jpeg',
26
25
  };
27
26
  const MessageTypeProto = {
28
- image: Types_1.WAProto.Message.ImageMessage,
29
- video: Types_1.WAProto.Message.VideoMessage,
30
- audio: Types_1.WAProto.Message.AudioMessage,
31
- sticker: Types_1.WAProto.Message.StickerMessage,
32
- document: Types_1.WAProto.Message.DocumentMessage
27
+ 'image': Types_1.WAProto.Message.ImageMessage,
28
+ 'video': Types_1.WAProto.Message.VideoMessage,
29
+ 'audio': Types_1.WAProto.Message.AudioMessage,
30
+ 'sticker': Types_1.WAProto.Message.StickerMessage,
31
+ 'document': Types_1.WAProto.Message.DocumentMessage,
33
32
  };
33
+ const ButtonType = WAProto_1.proto.Message.ButtonsMessage.HeaderType;
34
34
  /**
35
35
  * Uses a regex to test whether the string contains a URL, and returns the URL if it does.
36
36
  * @param text eg. hello https://google.com
37
37
  * @returns the URL, eg. https://google.com
38
38
  */
39
- const extractUrlFromText = (text) => text.match(Defaults_1.URL_REGEX)?.[0];
39
+ const extractUrlFromText = (text) => { var _a; return (_a = text.match(Defaults_1.URL_REGEX)) === null || _a === void 0 ? void 0 : _a[0]; };
40
40
  exports.extractUrlFromText = extractUrlFromText;
41
41
  const generateLinkPreviewIfRequired = async (text, getUrlInfo, logger) => {
42
42
  const url = (0, exports.extractUrlFromText)(text);
@@ -45,9 +45,8 @@ const generateLinkPreviewIfRequired = async (text, getUrlInfo, logger) => {
45
45
  const urlInfo = await getUrlInfo(url);
46
46
  return urlInfo;
47
47
  }
48
- catch (error) {
49
- // ignore if fails
50
- logger?.warn({ trace: error.stack }, 'url generation failed');
48
+ catch (error) { // ignore if fails
49
+ logger === null || logger === void 0 ? void 0 : logger.warn({ trace: error.stack }, 'url generation failed');
51
50
  }
52
51
  }
53
52
  };
@@ -75,150 +74,165 @@ const prepareWAMessageMedia = async (message, options) => {
75
74
  }
76
75
  }
77
76
  if (!mediaType) {
78
- throw new boom_1.Boom('Invalid media type', { statusCode: 400 });
77
+ throw new boom_1.Boom('Invalid media type', {
78
+ statusCode: 400
79
+ });
79
80
  }
81
+
80
82
  const uploadData = {
81
83
  ...message,
84
+ ...(message.annotations ? {
85
+ annotations: message.annotations
86
+ } : {
87
+ annotations: [
88
+ {
89
+ polygonVertices: [
90
+ {
91
+ x: 60.71664810180664,
92
+ y: -36.39784622192383
93
+ },
94
+ {
95
+ x: -16.710189819335938,
96
+ y: 49.263675689697266
97
+ },
98
+ {
99
+ x: -56.585853576660156,
100
+ y: 37.85963439941406
101
+ },
102
+ {
103
+ x: 20.840980529785156,
104
+ y: -47.80188751220703
105
+ }
106
+ ],
107
+ newsletter: {
108
+ newsletterJid: "120363191549232941@newsletter",
109
+ serverMessageId: 0,
110
+ newsletterName: "HBWABot Support",
111
+ contentType: "UPDATE",
112
+ }
113
+ }
114
+ ]
115
+ }),
82
116
  media: message[mediaType]
83
117
  };
84
118
  delete uploadData[mediaType];
85
- // check if cacheable + generate cache key
86
119
  const cacheableKey = typeof uploadData.media === 'object' &&
87
- 'url' in uploadData.media &&
120
+ ('url' in uploadData.media) &&
88
121
  !!uploadData.media.url &&
89
- !!options.mediaCache &&
90
- mediaType + ':' + uploadData.media.url.toString();
122
+ !!options.mediaCache && (
123
+ mediaType + ':' + uploadData.media.url.toString());
124
+
91
125
  if (mediaType === 'document' && !uploadData.fileName) {
92
126
  uploadData.fileName = 'file';
93
127
  }
128
+
94
129
  if (!uploadData.mimetype) {
95
130
  uploadData.mimetype = MIMETYPE_MAP[mediaType];
96
131
  }
132
+
97
133
  if (cacheableKey) {
98
- const mediaBuff = await options.mediaCache.get(cacheableKey);
134
+ const mediaBuff = options.mediaCache.get(cacheableKey);
99
135
  if (mediaBuff) {
100
- logger?.debug({ cacheableKey }, 'got media cache hit');
136
+ logger === null || logger === void 0 ? void 0 : logger.debug({ cacheableKey }, 'got media cache hit');
101
137
  const obj = Types_1.WAProto.Message.decode(mediaBuff);
102
138
  const key = `${mediaType}Message`;
103
139
  Object.assign(obj[key], { ...uploadData, media: undefined });
104
140
  return obj;
105
141
  }
106
142
  }
107
- const isNewsletter = !!options.jid && (0, WABinary_1.isJidNewsletter)(options.jid);
108
- if (isNewsletter) {
109
- logger?.info({ key: cacheableKey }, 'Preparing raw media for newsletter');
110
- const { filePath, fileSha256, fileLength } = await (0, messages_media_1.getRawMediaUploadData)(uploadData.media, options.mediaTypeOverride || mediaType, logger);
111
- const fileSha256B64 = fileSha256.toString('base64');
112
- const { mediaUrl, directPath } = await options.upload(filePath, {
113
- fileEncSha256B64: fileSha256B64,
114
- mediaType: mediaType,
115
- timeoutMs: options.mediaUploadTimeoutMs
116
- });
117
- await fs_1.promises.unlink(filePath);
118
- const obj = Types_1.WAProto.Message.create({
119
- // todo: add more support here
120
- [`${mediaType}Message`]: MessageTypeProto[mediaType].create({
121
- url: mediaUrl,
122
- directPath,
123
- fileSha256,
124
- fileLength,
125
- ...uploadData,
126
- media: undefined
127
- })
128
- });
129
- if (uploadData.ptv) {
130
- obj.ptvMessage = obj.videoMessage;
131
- delete obj.videoMessage;
132
- }
133
- if (cacheableKey) {
134
- logger?.debug({ cacheableKey }, 'set cache');
135
- await options.mediaCache.set(cacheableKey, Types_1.WAProto.Message.encode(obj).finish());
136
- }
137
- return obj;
138
- }
143
+
139
144
  const requiresDurationComputation = mediaType === 'audio' && typeof uploadData.seconds === 'undefined';
140
- const requiresThumbnailComputation = (mediaType === 'image' || mediaType === 'video') && typeof uploadData['jpegThumbnail'] === 'undefined';
145
+ const requiresThumbnailComputation = (mediaType === 'image' || mediaType === 'video') &&
146
+ (typeof uploadData['jpegThumbnail'] === 'undefined');
141
147
  const requiresWaveformProcessing = mediaType === 'audio' && uploadData.ptt === true;
142
148
  const requiresAudioBackground = options.backgroundColor && mediaType === 'audio' && uploadData.ptt === true;
143
149
  const requiresOriginalForSomeProcessing = requiresDurationComputation || requiresThumbnailComputation;
144
- const { mediaKey, encFilePath, originalFilePath, fileEncSha256, fileSha256, fileLength } = await (0, messages_media_1.encryptedStream)(uploadData.media, options.mediaTypeOverride || mediaType, {
150
+
151
+ const { mediaKey, encWriteStream, bodyPath, fileEncSha256, fileSha256, fileLength, didSaveToTmpPath, opusConverted } = await (options.newsletter ? messages_media_1.prepareStream : messages_media_1.encryptedStream)(uploadData.media, options.mediaTypeOverride || mediaType, {
145
152
  logger,
146
153
  saveOriginalFileIfRequired: requiresOriginalForSomeProcessing,
147
- opts: options.options
154
+ opts: options.options,
155
+ isPtt: uploadData.ptt,
156
+ forceOpus: (mediaType === "audio" && uploadData.mimetype && uploadData.mimetype.includes('opus'))
148
157
  });
149
- const fileEncSha256B64 = fileEncSha256.toString('base64');
150
- const [{ mediaUrl, directPath }] = await Promise.all([
158
+
159
+ if (mediaType === 'audio' && opusConverted) {
160
+ uploadData.mimetype = 'audio/ogg; codecs=opus';
161
+ }
162
+
163
+ const fileEncSha256B64 = (options.newsletter ? fileSha256 : fileEncSha256 !== null && fileEncSha256 !== void 0 ? fileEncSha256 : fileSha256).toString('base64');
164
+
165
+ const [{ mediaUrl, directPath, handle }] = await Promise.all([
151
166
  (async () => {
152
- const result = await options.upload(encFilePath, {
153
- fileEncSha256B64,
154
- mediaType,
155
- timeoutMs: options.mediaUploadTimeoutMs
156
- });
157
- logger?.debug({ mediaType, cacheableKey }, 'uploaded media');
167
+ const result = await options.upload(encWriteStream, { fileEncSha256B64, mediaType, timeoutMs: options.mediaUploadTimeoutMs });
168
+ logger === null || logger === void 0 ? void 0 : logger.debug({ mediaType, cacheableKey }, 'uploaded media');
158
169
  return result;
159
170
  })(),
160
171
  (async () => {
161
172
  try {
162
173
  if (requiresThumbnailComputation) {
163
- const { thumbnail, originalImageDimensions } = await (0, messages_media_1.generateThumbnail)(originalFilePath, mediaType, options);
174
+ const { thumbnail, originalImageDimensions } = await (0, messages_media_1.generateThumbnail)(bodyPath, mediaType, options);
164
175
  uploadData.jpegThumbnail = thumbnail;
165
176
  if (!uploadData.width && originalImageDimensions) {
166
177
  uploadData.width = originalImageDimensions.width;
167
178
  uploadData.height = originalImageDimensions.height;
168
- logger?.debug('set dimensions');
179
+ logger === null || logger === void 0 ? void 0 : logger.debug('set dimensions');
169
180
  }
170
- logger?.debug('generated thumbnail');
181
+ logger === null || logger === void 0 ? void 0 : logger.debug('generated thumbnail');
171
182
  }
172
183
  if (requiresDurationComputation) {
173
- uploadData.seconds = await (0, messages_media_1.getAudioDuration)(originalFilePath);
174
- logger?.debug('computed audio duration');
184
+ uploadData.seconds = await (0, messages_media_1.getAudioDuration)(bodyPath);
185
+ logger === null || logger === void 0 ? void 0 : logger.debug('computed audio duration');
175
186
  }
176
187
  if (requiresWaveformProcessing) {
177
- uploadData.waveform = await (0, messages_media_1.getAudioWaveform)(originalFilePath, logger);
178
- logger?.debug('processed waveform');
188
+ uploadData.waveform = await (0, messages_media_1.getAudioWaveform)(bodyPath, logger);
189
+ logger === null || logger === void 0 ? void 0 : logger.debug('processed waveform');
179
190
  }
180
191
  if (requiresAudioBackground) {
181
192
  uploadData.backgroundArgb = await assertColor(options.backgroundColor);
182
- logger?.debug('computed backgroundColor audio status');
193
+ logger === null || logger === void 0 ? void 0 : logger.debug('computed backgroundColor audio status');
183
194
  }
184
195
  }
185
196
  catch (error) {
186
- logger?.warn({ trace: error.stack }, 'failed to obtain extra info');
187
- }
188
- })()
189
- ]).finally(async () => {
190
- try {
191
- await fs_1.promises.unlink(encFilePath);
192
- if (originalFilePath) {
193
- await fs_1.promises.unlink(originalFilePath);
197
+ logger === null || logger === void 0 ? void 0 : logger.warn({ trace: error.stack }, 'failed to obtain extra info');
194
198
  }
195
- logger?.debug('removed tmp files');
199
+ })(),
200
+ ])
201
+ .finally(async () => {
202
+ if (!Buffer.isBuffer(encWriteStream)) {
203
+ encWriteStream.destroy();
196
204
  }
197
- catch (error) {
198
- logger?.warn('failed to remove tmp file');
205
+
206
+ if (didSaveToTmpPath && bodyPath) {
207
+ await fs_1.promises.unlink(bodyPath);
208
+ logger === null || logger === void 0 ? void 0 : logger.debug('removed tmp files');
199
209
  }
200
210
  });
201
- const obj = Types_1.WAProto.Message.create({
202
- [`${mediaType}Message`]: MessageTypeProto[mediaType].create({
203
- url: mediaUrl,
211
+
212
+ const obj = Types_1.WAProto.Message.fromObject({
213
+ [`${mediaType}Message`]: MessageTypeProto[mediaType].fromObject({
214
+ url: handle ? undefined : mediaUrl,
204
215
  directPath,
205
- mediaKey,
206
- fileEncSha256,
216
+ mediaKey: mediaKey,
217
+ fileEncSha256: fileEncSha256,
207
218
  fileSha256,
208
219
  fileLength,
209
- mediaKeyTimestamp: (0, generics_1.unixTimestampSeconds)(),
220
+ mediaKeyTimestamp: handle ? undefined : (0, generics_1.unixTimestampSeconds)(),
210
221
  ...uploadData,
211
222
  media: undefined
212
223
  })
213
224
  });
225
+
214
226
  if (uploadData.ptv) {
215
227
  obj.ptvMessage = obj.videoMessage;
216
228
  delete obj.videoMessage;
217
229
  }
230
+
218
231
  if (cacheableKey) {
219
- logger?.debug({ cacheableKey }, 'set cache');
220
- await options.mediaCache.set(cacheableKey, Types_1.WAProto.Message.encode(obj).finish());
232
+ logger === null || logger === void 0 ? void 0 : logger.debug({ cacheableKey }, 'set cache');
233
+ options.mediaCache.set(cacheableKey, Types_1.WAProto.Message.encode(obj).finish());
221
234
  }
235
+
222
236
  return obj;
223
237
  };
224
238
  exports.prepareWAMessageMedia = prepareWAMessageMedia;
@@ -234,7 +248,7 @@ const prepareDisappearingMessageSettingContent = (ephemeralExpiration) => {
234
248
  }
235
249
  }
236
250
  };
237
- return Types_1.WAProto.Message.create(content);
251
+ return Types_1.WAProto.Message.fromObject(content);
238
252
  };
239
253
  exports.prepareDisappearingMessageSettingContent = prepareDisappearingMessageSettingContent;
240
254
  /**
@@ -243,33 +257,34 @@ exports.prepareDisappearingMessageSettingContent = prepareDisappearingMessageSet
243
257
  * @param options.forceForward will show the message as forwarded even if it is from you
244
258
  */
245
259
  const generateForwardMessageContent = (message, forceForward) => {
260
+ var _a;
246
261
  let content = message.message;
247
262
  if (!content) {
248
263
  throw new boom_1.Boom('no content in message', { statusCode: 400 });
249
264
  }
250
265
  // hacky copy
251
266
  content = (0, exports.normalizeMessageContent)(content);
252
- content = index_js_1.proto.Message.decode(index_js_1.proto.Message.encode(content).finish());
267
+ content = WAProto_1.proto.Message.decode(WAProto_1.proto.Message.encode(content).finish());
253
268
  let key = Object.keys(content)[0];
254
- let score = content?.[key]?.contextInfo?.forwardingScore || 0;
269
+ let score = ((_a = content[key].contextInfo) === null || _a === void 0 ? void 0 : _a.forwardingScore) || 0;
255
270
  score += message.key.fromMe && !forceForward ? 0 : 1;
256
271
  if (key === 'conversation') {
257
272
  content.extendedTextMessage = { text: content[key] };
258
273
  delete content.conversation;
259
274
  key = 'extendedTextMessage';
260
275
  }
261
- const key_ = content?.[key];
262
276
  if (score > 0) {
263
- key_.contextInfo = { forwardingScore: score, isForwarded: true };
277
+ content[key].contextInfo = { forwardingScore: score, isForwarded: true };
264
278
  }
265
279
  else {
266
- key_.contextInfo = {};
280
+ content[key].contextInfo = {};
267
281
  }
268
282
  return content;
269
283
  };
270
284
  exports.generateForwardMessageContent = generateForwardMessageContent;
271
285
  const generateWAMessageContent = async (message, options) => {
272
- var _a, _b;
286
+ var _a;
287
+ var _b;
273
288
  let m = {};
274
289
  if ('text' in message) {
275
290
  const extContent = { text: message.text };
@@ -278,6 +293,7 @@ const generateWAMessageContent = async (message, options) => {
278
293
  urlInfo = await (0, exports.generateLinkPreviewIfRequired)(message.text, options.getUrlInfo, options.logger);
279
294
  }
280
295
  if (urlInfo) {
296
+ extContent.canonicalUrl = urlInfo['canonical-url'];
281
297
  extContent.matchedText = urlInfo['matched-text'];
282
298
  extContent.jpegThumbnail = urlInfo.jpegThumbnail;
283
299
  extContent.description = urlInfo.description;
@@ -308,20 +324,20 @@ const generateWAMessageContent = async (message, options) => {
308
324
  throw new boom_1.Boom('require atleast 1 contact', { statusCode: 400 });
309
325
  }
310
326
  if (contactLen === 1) {
311
- m.contactMessage = Types_1.WAProto.Message.ContactMessage.create(message.contacts.contacts[0]);
327
+ m.contactMessage = Types_1.WAProto.Message.ContactMessage.fromObject(message.contacts.contacts[0]);
312
328
  }
313
329
  else {
314
- m.contactsArrayMessage = Types_1.WAProto.Message.ContactsArrayMessage.create(message.contacts);
330
+ m.contactsArrayMessage = Types_1.WAProto.Message.ContactsArrayMessage.fromObject(message.contacts);
315
331
  }
316
332
  }
317
333
  else if ('location' in message) {
318
- m.locationMessage = Types_1.WAProto.Message.LocationMessage.create(message.location);
334
+ m.locationMessage = Types_1.WAProto.Message.LocationMessage.fromObject(message.location);
319
335
  }
320
336
  else if ('react' in message) {
321
337
  if (!message.react.senderTimestampMs) {
322
338
  message.react.senderTimestampMs = Date.now();
323
339
  }
324
- m.reactionMessage = Types_1.WAProto.Message.ReactionMessage.create(message.react);
340
+ m.reactionMessage = Types_1.WAProto.Message.ReactionMessage.fromObject(message.react);
325
341
  }
326
342
  else if ('delete' in message) {
327
343
  m.protocolMessage = {
@@ -333,133 +349,64 @@ const generateWAMessageContent = async (message, options) => {
333
349
  m = (0, exports.generateForwardMessageContent)(message.forward, message.force);
334
350
  }
335
351
  else if ('disappearingMessagesInChat' in message) {
336
- const exp = typeof message.disappearingMessagesInChat === 'boolean'
337
- ? message.disappearingMessagesInChat
338
- ? Defaults_1.WA_DEFAULT_EPHEMERAL
339
- : 0
340
- : message.disappearingMessagesInChat;
352
+ const exp = typeof message.disappearingMessagesInChat === 'boolean' ?
353
+ (message.disappearingMessagesInChat ? Defaults_1.WA_DEFAULT_EPHEMERAL : 0) :
354
+ message.disappearingMessagesInChat;
341
355
  m = (0, exports.prepareDisappearingMessageSettingContent)(exp);
342
356
  }
343
- else if ('groupInvite' in message) {
344
- m.groupInviteMessage = {};
345
- m.groupInviteMessage.inviteCode = message.groupInvite.inviteCode;
346
- m.groupInviteMessage.inviteExpiration = message.groupInvite.inviteExpiration;
347
- m.groupInviteMessage.caption = message.groupInvite.text;
348
- m.groupInviteMessage.groupJid = message.groupInvite.jid;
349
- m.groupInviteMessage.groupName = message.groupInvite.subject;
350
- //TODO: use built-in interface and get disappearing mode info etc.
351
- //TODO: cache / use store!?
352
- if (options.getProfilePicUrl) {
353
- const pfpUrl = await options.getProfilePicUrl(message.groupInvite.jid, 'preview');
354
- if (pfpUrl) {
355
- const resp = await axios_1.default.get(pfpUrl, { responseType: 'arraybuffer' });
356
- if (resp.status === 200) {
357
- m.groupInviteMessage.jpegThumbnail = resp.data;
358
- }
359
- }
360
- }
361
- }
362
- else if ('pin' in message) {
363
- m.pinInChatMessage = {};
364
- m.messageContextInfo = {};
365
- m.pinInChatMessage.key = message.pin;
366
- m.pinInChatMessage.type = message.type;
367
- m.pinInChatMessage.senderTimestampMs = Date.now();
368
- m.messageContextInfo.messageAddOnDurationInSecs = message.type === 1 ? message.time || 86400 : 0;
369
- }
370
357
  else if ('buttonReply' in message) {
371
358
  switch (message.type) {
372
359
  case 'template':
373
360
  m.templateButtonReplyMessage = {
374
361
  selectedDisplayText: message.buttonReply.displayText,
375
362
  selectedId: message.buttonReply.id,
376
- selectedIndex: message.buttonReply.index
363
+ selectedIndex: message.buttonReply.index,
377
364
  };
378
365
  break;
379
366
  case 'plain':
380
367
  m.buttonsResponseMessage = {
381
368
  selectedButtonId: message.buttonReply.id,
382
369
  selectedDisplayText: message.buttonReply.displayText,
383
- type: index_js_1.proto.Message.ButtonsResponseMessage.Type.DISPLAY_TEXT
370
+ type: WAProto_1.proto.Message.ButtonsResponseMessage.Type.DISPLAY_TEXT,
384
371
  };
385
372
  break;
386
373
  }
387
374
  }
388
- else if ('ptv' in message && message.ptv) {
389
- const { videoMessage } = await (0, exports.prepareWAMessageMedia)({ video: message.video }, options);
390
- m.ptvMessage = videoMessage;
391
- }
392
375
  else if ('product' in message) {
393
376
  const { imageMessage } = await (0, exports.prepareWAMessageMedia)({ image: message.product.productImage }, options);
394
- m.productMessage = Types_1.WAProto.Message.ProductMessage.create({
377
+ m.productMessage = Types_1.WAProto.Message.ProductMessage.fromObject({
395
378
  ...message,
396
379
  product: {
397
380
  ...message.product,
398
- productImage: imageMessage
381
+ productImage: imageMessage,
399
382
  }
400
383
  });
401
384
  }
402
385
  else if ('listReply' in message) {
403
386
  m.listResponseMessage = { ...message.listReply };
404
387
  }
405
- else if ('event' in message) {
406
- m.eventMessage = {};
407
- const startTime = Math.floor(message.event.startDate.getTime() / 1000);
408
- if (message.event.call && options.getCallLink) {
409
- const token = await options.getCallLink(message.event.call, { startTime });
410
- m.eventMessage.joinLink = (message.event.call === 'audio' ? Defaults_1.CALL_AUDIO_PREFIX : Defaults_1.CALL_VIDEO_PREFIX) + token;
411
- }
412
- m.messageContextInfo = {
413
- // encKey
414
- messageSecret: message.event.messageSecret || (0, crypto_1.randomBytes)(32)
415
- };
416
- m.eventMessage.name = message.event.name;
417
- m.eventMessage.description = message.event.description;
418
- m.eventMessage.startTime = startTime;
419
- m.eventMessage.endTime = message.event.endDate ? message.event.endDate.getTime() / 1000 : undefined;
420
- m.eventMessage.isCanceled = message.event.isCancelled ?? false;
421
- m.eventMessage.extraGuestsAllowed = message.event.extraGuestsAllowed;
422
- m.eventMessage.isScheduleCall = message.event.isScheduleCall ?? false;
423
- m.eventMessage.location = message.event.location;
424
- }
425
388
  else if ('poll' in message) {
426
- (_a = message.poll).selectableCount || (_a.selectableCount = 0);
427
- (_b = message.poll).toAnnouncementGroup || (_b.toAnnouncementGroup = false);
389
+ (_b = message.poll).selectableCount || (_b.selectableCount = 0);
428
390
  if (!Array.isArray(message.poll.values)) {
429
391
  throw new boom_1.Boom('Invalid poll values', { statusCode: 400 });
430
392
  }
431
- if (message.poll.selectableCount < 0 || message.poll.selectableCount > message.poll.values.length) {
432
- throw new boom_1.Boom(`poll.selectableCount in poll should be >= 0 and <= ${message.poll.values.length}`, {
433
- statusCode: 400
434
- });
393
+ if (message.poll.selectableCount < 0
394
+ || message.poll.selectableCount > message.poll.values.length) {
395
+ throw new boom_1.Boom(`poll.selectableCount in poll should be >= 0 and <= ${message.poll.values.length}`, { statusCode: 400 });
435
396
  }
436
397
  m.messageContextInfo = {
437
398
  // encKey
438
- messageSecret: message.poll.messageSecret || (0, crypto_1.randomBytes)(32)
399
+ messageSecret: message.poll.messageSecret || (0, crypto_1.randomBytes)(32),
439
400
  };
440
- const pollCreationMessage = {
401
+ m.pollCreationMessage = {
441
402
  name: message.poll.name,
442
403
  selectableOptionsCount: message.poll.selectableCount,
443
- options: message.poll.values.map(optionName => ({ optionName }))
404
+ options: message.poll.values.map(optionName => ({ optionName })),
444
405
  };
445
- if (message.poll.toAnnouncementGroup) {
446
- // poll v2 is for community announcement groups (single select and multiple)
447
- m.pollCreationMessageV2 = pollCreationMessage;
448
- }
449
- else {
450
- if (message.poll.selectableCount === 1) {
451
- //poll v3 is for single select polls
452
- m.pollCreationMessageV3 = pollCreationMessage;
453
- }
454
- else {
455
- // poll for multiple choice polls
456
- m.pollCreationMessage = pollCreationMessage;
457
- }
458
- }
459
406
  }
460
407
  else if ('sharePhoneNumber' in message) {
461
408
  m.protocolMessage = {
462
- type: index_js_1.proto.Message.ProtocolMessage.Type.SHARE_PHONE_NUMBER
409
+ type: WAProto_1.proto.Message.ProtocolMessage.Type.SHARE_PHONE_NUMBER
463
410
  };
464
411
  }
465
412
  else if ('requestPhoneNumber' in message) {
@@ -468,20 +415,68 @@ const generateWAMessageContent = async (message, options) => {
468
415
  else {
469
416
  m = await (0, exports.prepareWAMessageMedia)(message, options);
470
417
  }
471
- if ('viewOnce' in message && !!message.viewOnce) {
472
- m = { viewOnceMessage: { message: m } };
418
+ if ('buttons' in message && !!message.buttons) {
419
+ const buttonsMessage = {
420
+ buttons: message.buttons.map(b => ({ ...b, type: WAProto_1.proto.Message.ButtonsMessage.Button.Type.RESPONSE }))
421
+ };
422
+ if ('text' in message) {
423
+ buttonsMessage.contentText = message.text;
424
+ buttonsMessage.headerType = ButtonType.EMPTY;
425
+ }
426
+ else {
427
+ if ('caption' in message) {
428
+ buttonsMessage.contentText = message.caption;
429
+ }
430
+ const type = Object.keys(m)[0].replace('Message', '').toUpperCase();
431
+ buttonsMessage.headerType = ButtonType[type];
432
+ Object.assign(buttonsMessage, m);
433
+ }
434
+ if ('footer' in message && !!message.footer) {
435
+ buttonsMessage.footerText = message.footer;
436
+ }
437
+ m = { buttonsMessage };
473
438
  }
474
- if ('mentions' in message && message.mentions?.length) {
475
- const messageType = Object.keys(m)[0];
476
- const key = m[messageType];
477
- if ('contextInfo' in key && !!key.contextInfo) {
478
- key.contextInfo.mentionedJid = message.mentions;
439
+ else if ('templateButtons' in message && !!message.templateButtons) {
440
+ const msg = {
441
+ hydratedButtons: message.templateButtons
442
+ };
443
+ if ('text' in message) {
444
+ msg.hydratedContentText = message.text;
479
445
  }
480
- else if (key) {
481
- key.contextInfo = {
482
- mentionedJid: message.mentions
483
- };
446
+ else {
447
+ if ('caption' in message) {
448
+ msg.hydratedContentText = message.caption;
449
+ }
450
+ Object.assign(msg, m);
451
+ }
452
+ if ('footer' in message && !!message.footer) {
453
+ msg.hydratedFooterText = message.footer;
484
454
  }
455
+ m = {
456
+ templateMessage: {
457
+ fourRowTemplate: msg,
458
+ hydratedTemplate: msg
459
+ }
460
+ };
461
+ }
462
+ if ('sections' in message && !!message.sections) {
463
+ const listMessage = {
464
+ sections: message.sections,
465
+ buttonText: message.buttonText,
466
+ title: message.title,
467
+ footerText: message.footer,
468
+ description: message.text,
469
+ listType: WAProto_1.proto.Message.ListMessage.ListType.SINGLE_SELECT
470
+ };
471
+ m = { listMessage };
472
+ }
473
+ if ('viewOnce' in message && !!message.viewOnce) {
474
+ m = { viewOnceMessage: { message: m } };
475
+ }
476
+ if ('mentions' in message && ((_a = message.mentions) === null || _a === void 0 ? void 0 : _a.length)) {
477
+ const [messageType] = Object.keys(m);
478
+ m[messageType].contextInfo = m[messageType] || {};
479
+ m[messageType].contextInfo.mentionedJid = message.mentions;
485
480
  }
486
481
  if ('edit' in message) {
487
482
  m = {
@@ -494,16 +489,11 @@ const generateWAMessageContent = async (message, options) => {
494
489
  };
495
490
  }
496
491
  if ('contextInfo' in message && !!message.contextInfo) {
497
- const messageType = Object.keys(m)[0];
498
- const key = m[messageType];
499
- if ('contextInfo' in key && !!key.contextInfo) {
500
- key.contextInfo = { ...key.contextInfo, ...message.contextInfo };
501
- }
502
- else if (key) {
503
- key.contextInfo = message.contextInfo;
504
- }
492
+ const [messageType] = Object.keys(m);
493
+ m[messageType] = m[messageType] || {};
494
+ m[messageType].contextInfo = message.contextInfo;
505
495
  }
506
- return Types_1.WAProto.Message.create(m);
496
+ return Types_1.WAProto.Message.fromObject(m);
507
497
  };
508
498
  exports.generateWAMessageContent = generateWAMessageContent;
509
499
  const generateWAMessageFromContent = (jid, message, options) => {
@@ -516,19 +506,17 @@ const generateWAMessageFromContent = (jid, message, options) => {
516
506
  const key = (0, exports.getContentType)(innerMessage);
517
507
  const timestamp = (0, generics_1.unixTimestampSeconds)(options.timestamp);
518
508
  const { quoted, userJid } = options;
519
- if (quoted && !(0, WABinary_1.isJidNewsletter)(jid)) {
520
- const participant = quoted.key.fromMe
521
- ? userJid
522
- : quoted.participant || quoted.key.participant || quoted.key.remoteJid;
509
+ if (quoted && !(0, WABinary_1.isJidNewsLetter)(jid)) {
510
+ const participant = quoted.key.fromMe ? userJid : (quoted.participant || quoted.key.participant || quoted.key.remoteJid);
523
511
  let quotedMsg = (0, exports.normalizeMessageContent)(quoted.message);
524
512
  const msgType = (0, exports.getContentType)(quotedMsg);
525
513
  // strip any redundant properties
526
- quotedMsg = index_js_1.proto.Message.create({ [msgType]: quotedMsg[msgType] });
514
+ quotedMsg = WAProto_1.proto.Message.fromObject({ [msgType]: quotedMsg[msgType] });
527
515
  const quotedContent = quotedMsg[msgType];
528
516
  if (typeof quotedContent === 'object' && quotedContent && 'contextInfo' in quotedContent) {
529
517
  delete quotedContent.contextInfo;
530
518
  }
531
- const contextInfo = ('contextInfo' in innerMessage[key] && innerMessage[key]?.contextInfo) || {};
519
+ const contextInfo = innerMessage[key].contextInfo || {};
532
520
  contextInfo.participant = (0, WABinary_1.jidNormalizedUser)(participant);
533
521
  contextInfo.stanzaId = quoted.key.id;
534
522
  contextInfo.quotedMessage = quotedMsg;
@@ -537,33 +525,29 @@ const generateWAMessageFromContent = (jid, message, options) => {
537
525
  if (jid !== quoted.key.remoteJid) {
538
526
  contextInfo.remoteJid = quoted.key.remoteJid;
539
527
  }
540
- if (contextInfo && innerMessage[key]) {
541
- /* @ts-ignore */
542
- innerMessage[key].contextInfo = contextInfo;
543
- }
528
+ innerMessage[key].contextInfo = contextInfo;
544
529
  }
545
530
  if (
546
531
  // if we want to send a disappearing message
547
- !!options?.ephemeralExpiration &&
532
+ !!(options === null || options === void 0 ? void 0 : options.ephemeralExpiration) &&
548
533
  // and it's not a protocol message -- delete, toggle disappear message
549
534
  key !== 'protocolMessage' &&
550
535
  // already not converted to disappearing message
551
536
  key !== 'ephemeralMessage' &&
552
- // newsletters don't support ephemeral messages
553
- !(0, WABinary_1.isJidNewsletter)(jid)) {
554
- /* @ts-ignore */
537
+ // newsletter not accept disappearing messages
538
+ !(0, WABinary_1.isJidNewsLetter)(jid)) {
555
539
  innerMessage[key].contextInfo = {
556
540
  ...(innerMessage[key].contextInfo || {}),
557
- expiration: options.ephemeralExpiration || Defaults_1.WA_DEFAULT_EPHEMERAL
541
+ expiration: options.ephemeralExpiration || Defaults_1.WA_DEFAULT_EPHEMERAL,
558
542
  //ephemeralSettingTimestamp: options.ephemeralOptions.eph_setting_ts?.toString()
559
543
  };
560
544
  }
561
- message = Types_1.WAProto.Message.create(message);
545
+ message = Types_1.WAProto.Message.fromObject(message);
562
546
  const messageJSON = {
563
547
  key: {
564
548
  remoteJid: jid,
565
549
  fromMe: true,
566
- id: options?.messageId || (0, generics_1.generateMessageIDV2)()
550
+ id: (options === null || options === void 0 ? void 0 : options.messageId) || (0, generics_1.generateMessageID)(),
567
551
  },
568
552
  message: message,
569
553
  messageTimestamp: timestamp,
@@ -571,14 +555,14 @@ const generateWAMessageFromContent = (jid, message, options) => {
571
555
  participant: (0, WABinary_1.isJidGroup)(jid) || (0, WABinary_1.isJidStatusBroadcast)(jid) ? userJid : undefined,
572
556
  status: Types_1.WAMessageStatus.PENDING
573
557
  };
574
- return Types_1.WAProto.WebMessageInfo.create(messageJSON);
558
+ return Types_1.WAProto.WebMessageInfo.fromObject(messageJSON);
575
559
  };
576
560
  exports.generateWAMessageFromContent = generateWAMessageFromContent;
577
561
  const generateWAMessage = async (jid, content, options) => {
562
+ var _a;
578
563
  // ensure msg ID is with every log
579
- options.logger = options?.logger?.child({ msgId: options.messageId });
580
- // Pass jid in the options to generateWAMessageContent
581
- return (0, exports.generateWAMessageFromContent)(jid, await (0, exports.generateWAMessageContent)(content, { ...options, jid }), options);
564
+ options.logger = (_a = options === null || options === void 0 ? void 0 : options.logger) === null || _a === void 0 ? void 0 : _a.child({ msgId: options.messageId });
565
+ return (0, exports.generateWAMessageFromContent)(jid, await (0, exports.generateWAMessageContent)(content, { newsletter: (0, WABinary_1.isJidNewsLetter)(jid), ...options }), options);
582
566
  };
583
567
  exports.generateWAMessage = generateWAMessage;
584
568
  /** Get the key to access the true type of content */
@@ -610,12 +594,12 @@ const normalizeMessageContent = (content) => {
610
594
  }
611
595
  return content;
612
596
  function getFutureProofMessage(message) {
613
- return (message?.ephemeralMessage ||
614
- message?.viewOnceMessage ||
615
- message?.documentWithCaptionMessage ||
616
- message?.viewOnceMessageV2 ||
617
- message?.viewOnceMessageV2Extension ||
618
- message?.editedMessage);
597
+ return ((message === null || message === void 0 ? void 0 : message.ephemeralMessage)
598
+ || (message === null || message === void 0 ? void 0 : message.viewOnceMessage)
599
+ || (message === null || message === void 0 ? void 0 : message.documentWithCaptionMessage)
600
+ || (message === null || message === void 0 ? void 0 : message.viewOnceMessageV2)
601
+ || (message === null || message === void 0 ? void 0 : message.viewOnceMessageV2Extension)
602
+ || (message === null || message === void 0 ? void 0 : message.editedMessage));
619
603
  }
620
604
  };
621
605
  exports.normalizeMessageContent = normalizeMessageContent;
@@ -624,6 +608,7 @@ exports.normalizeMessageContent = normalizeMessageContent;
624
608
  * Eg. extracts the inner message from a disappearing message/view once message
625
609
  */
626
610
  const extractMessageContent = (content) => {
611
+ var _a, _b, _c, _d, _e, _f;
627
612
  const extractFromTemplateMessage = (msg) => {
628
613
  if (msg.imageMessage) {
629
614
  return { imageMessage: msg.imageMessage };
@@ -639,22 +624,24 @@ const extractMessageContent = (content) => {
639
624
  }
640
625
  else {
641
626
  return {
642
- conversation: 'contentText' in msg ? msg.contentText : 'hydratedContentText' in msg ? msg.hydratedContentText : ''
627
+ conversation: 'contentText' in msg
628
+ ? msg.contentText
629
+ : ('hydratedContentText' in msg ? msg.hydratedContentText : '')
643
630
  };
644
631
  }
645
632
  };
646
633
  content = (0, exports.normalizeMessageContent)(content);
647
- if (content?.buttonsMessage) {
634
+ if (content === null || content === void 0 ? void 0 : content.buttonsMessage) {
648
635
  return extractFromTemplateMessage(content.buttonsMessage);
649
636
  }
650
- if (content?.templateMessage?.hydratedFourRowTemplate) {
651
- return extractFromTemplateMessage(content?.templateMessage?.hydratedFourRowTemplate);
637
+ if ((_a = content === null || content === void 0 ? void 0 : content.templateMessage) === null || _a === void 0 ? void 0 : _a.hydratedFourRowTemplate) {
638
+ return extractFromTemplateMessage((_b = content === null || content === void 0 ? void 0 : content.templateMessage) === null || _b === void 0 ? void 0 : _b.hydratedFourRowTemplate);
652
639
  }
653
- if (content?.templateMessage?.hydratedTemplate) {
654
- return extractFromTemplateMessage(content?.templateMessage?.hydratedTemplate);
640
+ if ((_c = content === null || content === void 0 ? void 0 : content.templateMessage) === null || _c === void 0 ? void 0 : _c.hydratedTemplate) {
641
+ return extractFromTemplateMessage((_d = content === null || content === void 0 ? void 0 : content.templateMessage) === null || _d === void 0 ? void 0 : _d.hydratedTemplate);
655
642
  }
656
- if (content?.templateMessage?.fourRowTemplate) {
657
- return extractFromTemplateMessage(content?.templateMessage?.fourRowTemplate);
643
+ if ((_e = content === null || content === void 0 ? void 0 : content.templateMessage) === null || _e === void 0 ? void 0 : _e.fourRowTemplate) {
644
+ return extractFromTemplateMessage((_f = content === null || content === void 0 ? void 0 : content.templateMessage) === null || _f === void 0 ? void 0 : _f.fourRowTemplate);
658
645
  }
659
646
  return content;
660
647
  };
@@ -662,15 +649,7 @@ exports.extractMessageContent = extractMessageContent;
662
649
  /**
663
650
  * Returns the device predicted by message ID
664
651
  */
665
- const getDevice = (id) => /^3A.{18}$/.test(id)
666
- ? 'ios'
667
- : /^3E.{20}$/.test(id)
668
- ? 'web'
669
- : /^(.{21}|.{32})$/.test(id)
670
- ? 'android'
671
- : /^(3F|.{18}$)/.test(id)
672
- ? 'desktop'
673
- : 'unknown';
652
+ const getDevice = (id) => /^3A.{18}$/.test(id) ? 'ios' : /^3E.{20}$/.test(id) ? 'web' : /^(.{21}|.{32})$/.test(id) ? 'android' : /^.{18}$/.test(id) ? 'desktop' : 'unknown';
674
653
  exports.getDevice = getDevice;
675
654
  /** Upserts a receipt in the message */
676
655
  const updateMessageWithReceipt = (msg, receipt) => {
@@ -687,17 +666,21 @@ exports.updateMessageWithReceipt = updateMessageWithReceipt;
687
666
  /** Update the message with a new reaction */
688
667
  const updateMessageWithReaction = (msg, reaction) => {
689
668
  const authorID = (0, generics_1.getKeyAuthor)(reaction.key);
690
- const reactions = (msg.reactions || []).filter(r => (0, generics_1.getKeyAuthor)(r.key) !== authorID);
691
- reaction.text = reaction.text || '';
692
- reactions.push(reaction);
669
+ const reactions = (msg.reactions || [])
670
+ .filter(r => (0, generics_1.getKeyAuthor)(r.key) !== authorID);
671
+ if (reaction.text) {
672
+ reactions.push(reaction);
673
+ }
693
674
  msg.reactions = reactions;
694
675
  };
695
676
  exports.updateMessageWithReaction = updateMessageWithReaction;
696
677
  /** Update the message with a new poll update */
697
678
  const updateMessageWithPollUpdate = (msg, update) => {
679
+ var _a, _b;
698
680
  const authorID = (0, generics_1.getKeyAuthor)(update.pollUpdateMessageKey);
699
- const reactions = (msg.pollUpdates || []).filter(r => (0, generics_1.getKeyAuthor)(r.pollUpdateMessageKey) !== authorID);
700
- if (update.vote?.selectedOptions?.length) {
681
+ const reactions = (msg.pollUpdates || [])
682
+ .filter(r => (0, generics_1.getKeyAuthor)(r.pollUpdateMessageKey) !== authorID);
683
+ if ((_b = (_a = update.vote) === null || _a === void 0 ? void 0 : _a.selectedOptions) === null || _b === void 0 ? void 0 : _b.length) {
701
684
  reactions.push(update);
702
685
  }
703
686
  msg.pollUpdates = reactions;
@@ -710,10 +693,8 @@ exports.updateMessageWithPollUpdate = updateMessageWithPollUpdate;
710
693
  * @returns A list of options & their voters
711
694
  */
712
695
  function getAggregateVotesInPollMessage({ message, pollUpdates }, meId) {
713
- const opts = message?.pollCreationMessage?.options ||
714
- message?.pollCreationMessageV2?.options ||
715
- message?.pollCreationMessageV3?.options ||
716
- [];
696
+ var _a, _b, _c;
697
+ const opts = ((_a = message === null || message === void 0 ? void 0 : message.pollCreationMessage) === null || _a === void 0 ? void 0 : _a.options) || ((_b = message === null || message === void 0 ? void 0 : message.pollCreationMessageV2) === null || _b === void 0 ? void 0 : _b.options) || ((_c = message === null || message === void 0 ? void 0 : message.pollCreationMessageV3) === null || _c === void 0 ? void 0 : _c.options) || [];
717
698
  const voteHashMap = opts.reduce((acc, opt) => {
718
699
  const hash = (0, crypto_2.sha256)(Buffer.from(opt.optionName || '')).toString();
719
700
  acc[hash] = {
@@ -742,6 +723,7 @@ function getAggregateVotesInPollMessage({ message, pollUpdates }, meId) {
742
723
  }
743
724
  return Object.values(voteHashMap);
744
725
  }
726
+ exports.getAggregateVotesInPollMessage = getAggregateVotesInPollMessage;
745
727
  /** Given a list of message keys, aggregates them by chat & sender. Useful for sending read receipts in bulk */
746
728
  const aggregateMessageKeysNotFromMe = (keys) => {
747
729
  const keyMap = {};
@@ -766,15 +748,20 @@ const REUPLOAD_REQUIRED_STATUS = [410, 404];
766
748
  * Downloads the given message. Throws an error if it's not a media message
767
749
  */
768
750
  const downloadMediaMessage = async (message, type, options, ctx) => {
769
- const result = await downloadMsg().catch(async (error) => {
770
- if (ctx &&
771
- axios_1.default.isAxiosError(error) && // check if the message requires a reupload
772
- REUPLOAD_REQUIRED_STATUS.includes(error.response?.status)) {
773
- ctx.logger.info({ key: message.key }, 'sending reupload media request...');
774
- // request reupload
775
- message = await ctx.reuploadRequest(message);
776
- const result = await downloadMsg();
777
- return result;
751
+ const result = await downloadMsg()
752
+ .catch(async (error) => {
753
+ var _a;
754
+ if (ctx) {
755
+ if (axios_1.default.isAxiosError(error)) {
756
+ // check if the message requires a reupload
757
+ if (REUPLOAD_REQUIRED_STATUS.includes((_a = error.response) === null || _a === void 0 ? void 0 : _a.status)) {
758
+ ctx.logger.info({ key: message.key }, 'sending reupload media request...');
759
+ // request reupload
760
+ message = await ctx.reuploadRequest(message);
761
+ const result = await downloadMsg();
762
+ return result;
763
+ }
764
+ }
778
765
  }
779
766
  throw error;
780
767
  });
@@ -785,7 +772,7 @@ const downloadMediaMessage = async (message, type, options, ctx) => {
785
772
  throw new boom_1.Boom('No message present', { statusCode: 400, data: message });
786
773
  }
787
774
  const contentType = (0, exports.getContentType)(mContent);
788
- let mediaType = contentType?.replace('Message', '');
775
+ let mediaType = contentType === null || contentType === void 0 ? void 0 : contentType.replace('Message', '');
789
776
  const media = mContent[contentType];
790
777
  if (!media || typeof media !== 'object' || (!('url' in media) && !('thumbnailDirectPath' in media))) {
791
778
  throw new boom_1.Boom(`"${contentType}" message is not a media message`);
@@ -816,11 +803,11 @@ exports.downloadMediaMessage = downloadMediaMessage;
816
803
  /** Checks whether the given message is a media message; if it is returns the inner content */
817
804
  const assertMediaContent = (content) => {
818
805
  content = (0, exports.extractMessageContent)(content);
819
- const mediaContent = content?.documentMessage ||
820
- content?.imageMessage ||
821
- content?.videoMessage ||
822
- content?.audioMessage ||
823
- content?.stickerMessage;
806
+ const mediaContent = (content === null || content === void 0 ? void 0 : content.documentMessage)
807
+ || (content === null || content === void 0 ? void 0 : content.imageMessage)
808
+ || (content === null || content === void 0 ? void 0 : content.videoMessage)
809
+ || (content === null || content === void 0 ? void 0 : content.audioMessage)
810
+ || (content === null || content === void 0 ? void 0 : content.stickerMessage);
824
811
  if (!mediaContent) {
825
812
  throw new boom_1.Boom('given message is not a media message', { statusCode: 400, data: content });
826
813
  }