@queenanya/baileys 9.2.1 → 9.4.1
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 +349 -1171
- package/WAProto/fix-imports.js +74 -18
- package/WAProto/index.js +201 -160
- package/engine-requirements.js +7 -7
- package/lib/Defaults/index.d.ts +19 -0
- package/lib/Defaults/index.d.ts.map +1 -1
- package/lib/Defaults/index.js +32 -6
- package/lib/Defaults/index.js.map +1 -1
- package/lib/Signal/libsignal.d.ts.map +1 -1
- package/lib/Signal/libsignal.js +61 -2
- package/lib/Signal/libsignal.js.map +1 -1
- package/lib/Signal/lid-mapping.d.ts +5 -9
- package/lib/Signal/lid-mapping.d.ts.map +1 -1
- package/lib/Signal/lid-mapping.js +170 -70
- package/lib/Signal/lid-mapping.js.map +1 -1
- package/lib/Socket/Client/websocket.d.ts +1 -1
- package/lib/Socket/Client/websocket.d.ts.map +1 -1
- package/lib/Socket/Client/websocket.js +5 -1
- package/lib/Socket/Client/websocket.js.map +1 -1
- package/lib/Socket/business.d.ts +125 -5
- package/lib/Socket/business.d.ts.map +1 -1
- package/lib/Socket/business.js +11 -8
- package/lib/Socket/business.js.map +1 -1
- package/lib/Socket/chats.d.ts +22 -3
- package/lib/Socket/chats.d.ts.map +1 -1
- package/lib/Socket/chats.js +277 -58
- package/lib/Socket/chats.js.map +1 -1
- package/lib/Socket/communities.d.ts +125 -5
- package/lib/Socket/communities.d.ts.map +1 -1
- package/lib/Socket/groups.d.ts +19 -3
- package/lib/Socket/groups.d.ts.map +1 -1
- package/lib/Socket/groups.js +7 -1
- package/lib/Socket/groups.js.map +1 -1
- package/lib/Socket/index.d.ts +125 -5
- package/lib/Socket/index.d.ts.map +1 -1
- package/lib/Socket/index.js +0 -6
- package/lib/Socket/index.js.map +1 -1
- package/lib/Socket/messages-recv.d.ts +126 -6
- package/lib/Socket/messages-recv.d.ts.map +1 -1
- package/lib/Socket/messages-recv.js +771 -177
- package/lib/Socket/messages-recv.js.map +1 -1
- package/lib/Socket/messages-send.d.ts +129 -7
- package/lib/Socket/messages-send.d.ts.map +1 -1
- package/lib/Socket/messages-send.js +430 -119
- package/lib/Socket/messages-send.js.map +1 -1
- package/lib/Socket/newsletter.d.ts +20 -5
- package/lib/Socket/newsletter.d.ts.map +1 -1
- package/lib/Socket/newsletter.js +2 -47
- package/lib/Socket/newsletter.js.map +1 -1
- package/lib/Socket/socket.d.ts +3 -1
- package/lib/Socket/socket.d.ts.map +1 -1
- package/lib/Socket/socket.js +151 -29
- package/lib/Socket/socket.js.map +1 -1
- package/lib/Types/Auth.d.ts +2 -0
- package/lib/Types/Auth.d.ts.map +1 -1
- package/lib/Types/Call.d.ts +10 -1
- package/lib/Types/Call.d.ts.map +1 -1
- package/lib/Types/Contact.d.ts +2 -0
- package/lib/Types/Contact.d.ts.map +1 -1
- package/lib/Types/Events.d.ts +60 -6
- package/lib/Types/Events.d.ts.map +1 -1
- package/lib/Types/GroupMetadata.d.ts +4 -0
- package/lib/Types/GroupMetadata.d.ts.map +1 -1
- package/lib/Types/Message.d.ts +530 -16
- package/lib/Types/Message.d.ts.map +1 -1
- package/lib/Types/Message.js.map +1 -1
- package/lib/Types/Newsletter.d.ts +32 -45
- package/lib/Types/Newsletter.d.ts.map +1 -1
- package/lib/Types/Newsletter.js +25 -23
- package/lib/Types/Newsletter.js.map +1 -1
- package/lib/Types/State.d.ts +54 -0
- package/lib/Types/State.d.ts.map +1 -1
- package/lib/Types/State.js +42 -0
- package/lib/Types/State.js.map +1 -1
- package/lib/Types/index.d.ts +9 -0
- package/lib/Types/index.d.ts.map +1 -1
- package/lib/Types/index.js.map +1 -1
- package/lib/Utils/auth-utils.d.ts.map +1 -1
- package/lib/Utils/auth-utils.js +53 -20
- package/lib/Utils/auth-utils.js.map +1 -1
- package/lib/Utils/browser-utils.d.ts +13 -0
- package/lib/Utils/browser-utils.d.ts.map +1 -1
- package/lib/Utils/browser-utils.js +90 -10
- package/lib/Utils/browser-utils.js.map +1 -1
- package/lib/Utils/chat-utils.d.ts +30 -0
- package/lib/Utils/chat-utils.d.ts.map +1 -1
- package/lib/Utils/chat-utils.js +134 -59
- package/lib/Utils/chat-utils.js.map +1 -1
- package/lib/Utils/companion-reg-client-utils.d.ts +17 -0
- package/lib/Utils/companion-reg-client-utils.d.ts.map +1 -0
- package/lib/Utils/companion-reg-client-utils.js +34 -0
- package/lib/Utils/companion-reg-client-utils.js.map +1 -0
- package/lib/Utils/crypto.d.ts +4 -8
- package/lib/Utils/crypto.d.ts.map +1 -1
- package/lib/Utils/crypto.js +2 -26
- package/lib/Utils/crypto.js.map +1 -1
- package/lib/Utils/decode-wa-message.d.ts +12 -0
- package/lib/Utils/decode-wa-message.d.ts.map +1 -1
- package/lib/Utils/decode-wa-message.js +16 -0
- package/lib/Utils/decode-wa-message.js.map +1 -1
- package/lib/Utils/event-buffer.d.ts.map +1 -1
- package/lib/Utils/event-buffer.js +43 -8
- package/lib/Utils/event-buffer.js.map +1 -1
- package/lib/Utils/generics.d.ts +3 -1
- package/lib/Utils/generics.d.ts.map +1 -1
- package/lib/Utils/generics.js +17 -4
- package/lib/Utils/generics.js.map +1 -1
- package/lib/Utils/history.d.ts +8 -3
- package/lib/Utils/history.d.ts.map +1 -1
- package/lib/Utils/history.js +60 -16
- package/lib/Utils/history.js.map +1 -1
- package/lib/Utils/identity-change-handler.d.ts +44 -0
- package/lib/Utils/identity-change-handler.d.ts.map +1 -0
- package/lib/Utils/identity-change-handler.js +50 -0
- package/lib/Utils/identity-change-handler.js.map +1 -0
- package/lib/Utils/index.d.ts +6 -0
- package/lib/Utils/index.d.ts.map +1 -1
- package/lib/Utils/index.js +6 -0
- package/lib/Utils/index.js.map +1 -1
- package/lib/Utils/interactive-message.d.ts +201 -0
- package/lib/Utils/interactive-message.d.ts.map +1 -0
- package/lib/Utils/interactive-message.js +256 -0
- package/lib/Utils/interactive-message.js.map +1 -0
- package/lib/Utils/lt-hash.d.ts +7 -12
- package/lib/Utils/lt-hash.d.ts.map +1 -1
- package/lib/Utils/lt-hash.js +2 -42
- package/lib/Utils/lt-hash.js.map +1 -1
- package/lib/Utils/make-mutex.d.ts +1 -0
- package/lib/Utils/make-mutex.d.ts.map +1 -1
- package/lib/Utils/make-mutex.js +20 -27
- package/lib/Utils/make-mutex.js.map +1 -1
- package/lib/Utils/message-composer.d.ts +5 -0
- package/lib/Utils/message-composer.d.ts.map +1 -0
- package/lib/Utils/message-composer.js +5 -0
- package/lib/Utils/message-composer.js.map +1 -0
- package/lib/Utils/message-retry-manager.d.ts +30 -2
- package/lib/Utils/message-retry-manager.d.ts.map +1 -1
- package/lib/Utils/message-retry-manager.js +58 -5
- package/lib/Utils/message-retry-manager.js.map +1 -1
- package/lib/Utils/messages-media.d.ts +35 -5
- package/lib/Utils/messages-media.d.ts.map +1 -1
- package/lib/Utils/messages-media.js +171 -51
- package/lib/Utils/messages-media.js.map +1 -1
- package/lib/Utils/messages.d.ts +2 -0
- package/lib/Utils/messages.d.ts.map +1 -1
- package/lib/Utils/messages.js +475 -35
- package/lib/Utils/messages.js.map +1 -1
- package/lib/Utils/noise-handler.d.ts +4 -4
- package/lib/Utils/noise-handler.d.ts.map +1 -1
- package/lib/Utils/noise-handler.js +139 -85
- package/lib/Utils/noise-handler.js.map +1 -1
- package/lib/Utils/offline-node-processor.d.ts +17 -0
- package/lib/Utils/offline-node-processor.d.ts.map +1 -0
- package/lib/Utils/offline-node-processor.js +40 -0
- package/lib/Utils/offline-node-processor.js.map +1 -0
- package/lib/Utils/process-message.d.ts.map +1 -1
- package/lib/Utils/process-message.js +115 -16
- package/lib/Utils/process-message.js.map +1 -1
- package/lib/Utils/reporting-utils.d.ts +11 -0
- package/lib/Utils/reporting-utils.d.ts.map +1 -0
- package/lib/Utils/reporting-utils.js +258 -0
- package/lib/Utils/reporting-utils.js.map +1 -0
- package/lib/Utils/stanza-ack.d.ts +11 -0
- package/lib/Utils/stanza-ack.d.ts.map +1 -0
- package/lib/Utils/stanza-ack.js +38 -0
- package/lib/Utils/stanza-ack.js.map +1 -0
- package/lib/Utils/sync-action-utils.d.ts +19 -0
- package/lib/Utils/sync-action-utils.d.ts.map +1 -0
- package/lib/Utils/sync-action-utils.js +49 -0
- package/lib/Utils/sync-action-utils.js.map +1 -0
- package/lib/Utils/tc-token-utils.d.ts +37 -0
- package/lib/Utils/tc-token-utils.d.ts.map +1 -0
- package/lib/Utils/tc-token-utils.js +163 -0
- package/lib/Utils/tc-token-utils.js.map +1 -0
- package/lib/Utils/use-mongo-file-auth-state.d.ts +16 -0
- package/lib/Utils/use-mongo-file-auth-state.d.ts.map +1 -0
- package/lib/Utils/use-mongo-file-auth-state.js +60 -0
- package/lib/Utils/use-mongo-file-auth-state.js.map +1 -0
- package/lib/Utils/use-multi-file-auth-state.js +1 -1
- package/lib/Utils/use-multi-file-auth-state.js.map +1 -1
- package/lib/Utils/use-single-file-auth-state.d.ts.map +1 -1
- package/lib/Utils/use-single-file-auth-state.js.map +1 -1
- package/lib/Utils/validate-connection.d.ts.map +1 -1
- package/lib/Utils/validate-connection.js +11 -1
- package/lib/Utils/validate-connection.js.map +1 -1
- package/lib/WABinary/decode.d.ts.map +1 -1
- package/lib/WABinary/decode.js +24 -0
- package/lib/WABinary/decode.js.map +1 -1
- package/lib/WABinary/encode.js +5 -1
- package/lib/WABinary/encode.js.map +1 -1
- package/lib/WABinary/generic-utils.d.ts +10 -1
- package/lib/WABinary/generic-utils.d.ts.map +1 -1
- package/lib/WABinary/generic-utils.js +42 -8
- package/lib/WABinary/generic-utils.js.map +1 -1
- package/lib/WABinary/jid-utils.js.map +1 -1
- package/lib/WAUSync/Protocols/USyncContactProtocol.d.ts.map +1 -1
- package/lib/WAUSync/Protocols/USyncContactProtocol.js +26 -3
- package/lib/WAUSync/Protocols/USyncContactProtocol.js.map +1 -1
- package/lib/WAUSync/Protocols/USyncUsernameProtocol.d.ts +10 -0
- package/lib/WAUSync/Protocols/USyncUsernameProtocol.d.ts.map +1 -0
- package/lib/WAUSync/Protocols/USyncUsernameProtocol.js +25 -0
- package/lib/WAUSync/Protocols/USyncUsernameProtocol.js.map +1 -0
- package/lib/WAUSync/Protocols/index.d.ts +1 -0
- package/lib/WAUSync/Protocols/index.d.ts.map +1 -1
- package/lib/WAUSync/Protocols/index.js +1 -0
- package/lib/WAUSync/Protocols/index.js.map +1 -1
- package/lib/WAUSync/USyncQuery.d.ts +1 -0
- package/lib/WAUSync/USyncQuery.d.ts.map +1 -1
- package/lib/WAUSync/USyncQuery.js +6 -2
- package/lib/WAUSync/USyncQuery.js.map +1 -1
- package/lib/WAUSync/USyncUser.d.ts +4 -0
- package/lib/WAUSync/USyncUser.d.ts.map +1 -1
- package/lib/WAUSync/USyncUser.js +8 -0
- package/lib/WAUSync/USyncUser.js.map +1 -1
- package/lib/addons/anti-delete.d.ts +72 -0
- package/lib/addons/anti-delete.d.ts.map +1 -0
- package/lib/addons/anti-delete.js +165 -0
- package/lib/addons/anti-delete.js.map +1 -0
- package/lib/addons/auto-reply.d.ts +67 -0
- package/lib/addons/auto-reply.d.ts.map +1 -0
- package/lib/addons/auto-reply.js +145 -0
- package/lib/addons/auto-reply.js.map +1 -0
- package/lib/addons/browser-presets.d.ts +16 -0
- package/lib/addons/browser-presets.d.ts.map +1 -0
- package/lib/addons/browser-presets.js +24 -0
- package/lib/addons/browser-presets.js.map +1 -0
- package/lib/addons/button-sender.d.ts +260 -0
- package/lib/addons/button-sender.d.ts.map +1 -0
- package/lib/addons/button-sender.js +771 -0
- package/lib/addons/button-sender.js.map +1 -0
- package/lib/addons/call-handler.d.ts +79 -0
- package/lib/addons/call-handler.d.ts.map +1 -0
- package/lib/addons/call-handler.js +342 -0
- package/lib/addons/call-handler.js.map +1 -0
- package/lib/addons/from-chats.d.ts +30 -0
- package/lib/addons/from-chats.d.ts.map +1 -0
- package/lib/addons/from-chats.js +38 -0
- package/lib/addons/from-chats.js.map +1 -0
- package/lib/addons/from-messages-recv.d.ts +59 -0
- package/lib/addons/from-messages-recv.d.ts.map +1 -0
- package/lib/addons/from-messages-recv.js +326 -0
- package/lib/addons/from-messages-recv.js.map +1 -0
- package/lib/addons/from-messages-send.d.ts +50 -0
- package/lib/addons/from-messages-send.d.ts.map +1 -0
- package/lib/addons/from-messages-send.js +148 -0
- package/lib/addons/from-messages-send.js.map +1 -0
- package/lib/addons/from-messages.d.ts +52 -0
- package/lib/addons/from-messages.d.ts.map +1 -0
- package/lib/addons/from-messages.js +304 -0
- package/lib/addons/from-messages.js.map +1 -0
- package/lib/addons/index.d.ts +67 -0
- package/lib/addons/index.d.ts.map +1 -0
- package/lib/addons/index.js +86 -0
- package/lib/addons/index.js.map +1 -0
- package/lib/addons/interactive-message.d.ts +201 -0
- package/lib/addons/interactive-message.d.ts.map +1 -0
- package/lib/addons/interactive-message.js +256 -0
- package/lib/addons/interactive-message.js.map +1 -0
- package/lib/addons/jid-plot.d.ts +49 -0
- package/lib/addons/jid-plot.d.ts.map +1 -0
- package/lib/addons/jid-plot.js +84 -0
- package/lib/addons/jid-plot.js.map +1 -0
- package/lib/addons/jid-plotting.d.ts +54 -0
- package/lib/addons/jid-plotting.d.ts.map +1 -0
- package/lib/addons/jid-plotting.js +150 -0
- package/lib/addons/jid-plotting.js.map +1 -0
- package/lib/addons/lid-support.d.ts +41 -0
- package/lib/addons/lid-support.d.ts.map +1 -0
- package/lib/addons/lid-support.js +42 -0
- package/lib/addons/lid-support.js.map +1 -0
- package/lib/addons/message-composer.d.ts +142 -0
- package/lib/addons/message-composer.d.ts.map +1 -0
- package/lib/addons/message-composer.js +377 -0
- package/lib/addons/message-composer.js.map +1 -0
- package/lib/addons/message-scheduler.d.ts +77 -0
- package/lib/addons/message-scheduler.d.ts.map +1 -0
- package/lib/addons/message-scheduler.js +108 -0
- package/lib/addons/message-scheduler.js.map +1 -0
- package/lib/addons/message-search.d.ts +51 -0
- package/lib/addons/message-search.d.ts.map +1 -0
- package/lib/addons/message-search.js +171 -0
- package/lib/addons/message-search.js.map +1 -0
- package/lib/addons/message-utils.d.ts +88 -0
- package/lib/addons/message-utils.d.ts.map +1 -0
- package/lib/addons/message-utils.js +292 -0
- package/lib/addons/message-utils.js.map +1 -0
- package/lib/addons/outgoing-calls.d.ts +64 -0
- package/lib/addons/outgoing-calls.d.ts.map +1 -0
- package/lib/addons/outgoing-calls.js +139 -0
- package/lib/addons/outgoing-calls.js.map +1 -0
- package/lib/addons/pairing-fix.d.ts +31 -0
- package/lib/addons/pairing-fix.d.ts.map +1 -0
- package/lib/addons/pairing-fix.js +74 -0
- package/lib/addons/pairing-fix.js.map +1 -0
- package/lib/addons/past-participants.d.ts +42 -0
- package/lib/addons/past-participants.d.ts.map +1 -0
- package/lib/addons/past-participants.js +41 -0
- package/lib/addons/past-participants.js.map +1 -0
- package/lib/addons/rich-response.d.ts +111 -0
- package/lib/addons/rich-response.d.ts.map +1 -0
- package/lib/addons/rich-response.js +152 -0
- package/lib/addons/rich-response.js.map +1 -0
- package/lib/addons/scheduling.d.ts +41 -0
- package/lib/addons/scheduling.d.ts.map +1 -0
- package/lib/addons/scheduling.js +110 -0
- package/lib/addons/scheduling.js.map +1 -0
- package/lib/addons/status-posting.d.ts +177 -0
- package/lib/addons/status-posting.d.ts.map +1 -0
- package/lib/addons/status-posting.js +240 -0
- package/lib/addons/status-posting.js.map +1 -0
- package/lib/addons/stickerpack.d.ts +37 -0
- package/lib/addons/stickerpack.d.ts.map +1 -0
- package/lib/addons/stickerpack.js +39 -0
- package/lib/addons/stickerpack.js.map +1 -0
- package/lib/addons/templates.d.ts +72 -0
- package/lib/addons/templates.d.ts.map +1 -0
- package/lib/addons/templates.js +145 -0
- package/lib/addons/templates.js.map +1 -0
- package/lib/addons/vcard.d.ts +59 -0
- package/lib/addons/vcard.d.ts.map +1 -0
- package/lib/addons/vcard.js +88 -0
- package/lib/addons/vcard.js.map +1 -0
- package/lib/index.d.ts +1 -0
- package/lib/index.d.ts.map +1 -1
- package/lib/index.js +1 -0
- package/lib/index.js.map +1 -1
- package/package.json +6 -3
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"message-composer.js","sourceRoot":"","sources":["../../src/Utils/message-composer.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,cAAc,4BAA4B,CAAA"}
|
|
@@ -23,6 +23,24 @@ export interface RetryStatistics {
|
|
|
23
23
|
sessionRecreations: number;
|
|
24
24
|
phoneRequests: number;
|
|
25
25
|
}
|
|
26
|
+
export declare enum RetryReason {
|
|
27
|
+
UnknownError = 0,
|
|
28
|
+
SignalErrorNoSession = 1,
|
|
29
|
+
SignalErrorInvalidKey = 2,
|
|
30
|
+
SignalErrorInvalidKeyId = 3,
|
|
31
|
+
/** MAC verification failed - most common cause of decryption failures */
|
|
32
|
+
SignalErrorInvalidMessage = 4,
|
|
33
|
+
SignalErrorInvalidSignature = 5,
|
|
34
|
+
SignalErrorFutureMessage = 6,
|
|
35
|
+
/** Explicit MAC failure - session is definitely out of sync */
|
|
36
|
+
SignalErrorBadMac = 7,
|
|
37
|
+
SignalErrorInvalidSession = 8,
|
|
38
|
+
SignalErrorInvalidMsgKey = 9,
|
|
39
|
+
BadBroadcastEphemeralSetting = 10,
|
|
40
|
+
UnknownCompanionNoPrekey = 11,
|
|
41
|
+
AdvFailure = 12,
|
|
42
|
+
StatusRevokeDelay = 13
|
|
43
|
+
}
|
|
26
44
|
export declare class MessageRetryManager {
|
|
27
45
|
private logger;
|
|
28
46
|
private recentMessagesMap;
|
|
@@ -42,12 +60,22 @@ export declare class MessageRetryManager {
|
|
|
42
60
|
*/
|
|
43
61
|
getRecentMessage(to: string, id: string): RecentMessage | undefined;
|
|
44
62
|
/**
|
|
45
|
-
* Check if a session should be recreated based on retry count and
|
|
63
|
+
* Check if a session should be recreated based on retry count, history, and error code.
|
|
64
|
+
* MAC errors (codes 4 and 7) trigger immediate session recreation regardless of timeout.
|
|
46
65
|
*/
|
|
47
|
-
shouldRecreateSession(jid: string,
|
|
66
|
+
shouldRecreateSession(jid: string, hasSession: boolean, errorCode?: RetryReason): {
|
|
48
67
|
reason: string;
|
|
49
68
|
recreate: boolean;
|
|
50
69
|
};
|
|
70
|
+
/**
|
|
71
|
+
* Parse error code from retry receipt's retry node.
|
|
72
|
+
* Returns undefined if no error code is present.
|
|
73
|
+
*/
|
|
74
|
+
parseRetryErrorCode(errorAttr: string | undefined): RetryReason | undefined;
|
|
75
|
+
/**
|
|
76
|
+
* Check if an error code indicates a MAC failure
|
|
77
|
+
*/
|
|
78
|
+
isMacError(errorCode: RetryReason | undefined): boolean;
|
|
51
79
|
/**
|
|
52
80
|
* Increment retry counter for a message
|
|
53
81
|
*/
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"message-retry-manager.d.ts","sourceRoot":"","sources":["../../src/Utils/message-retry-manager.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,wBAAwB,CAAA;AACnD,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,UAAU,CAAA;AAUvC,MAAM,WAAW,gBAAgB;IAChC,EAAE,EAAE,MAAM,CAAA;IACV,EAAE,EAAE,MAAM,CAAA;CACV;AAED,MAAM,WAAW,aAAa;IAC7B,OAAO,EAAE,KAAK,CAAC,QAAQ,CAAA;IACvB,SAAS,EAAE,MAAM,CAAA;CACjB;AAED,MAAM,WAAW,sBAAsB;IACtC,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAAA;CACrB;AAED,MAAM,WAAW,YAAY;IAC5B,CAAC,SAAS,EAAE,MAAM,GAAG,MAAM,CAAA;CAC3B;AAED,MAAM,MAAM,mBAAmB,GAAG,MAAM,CAAC,MAAM,EAAE,UAAU,CAAC,OAAO,UAAU,CAAC,CAAC,CAAA;AAE/E,MAAM,WAAW,eAAe;IAC/B,YAAY,EAAE,MAAM,CAAA;IACpB,iBAAiB,EAAE,MAAM,CAAA;IACzB,aAAa,EAAE,MAAM,CAAA;IACrB,YAAY,EAAE,MAAM,CAAA;IACpB,kBAAkB,EAAE,MAAM,CAAA;IAC1B,aAAa,EAAE,MAAM,CAAA;CACrB;
|
|
1
|
+
{"version":3,"file":"message-retry-manager.d.ts","sourceRoot":"","sources":["../../src/Utils/message-retry-manager.ts"],"names":[],"mappings":"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"}
|
|
@@ -5,6 +5,28 @@ const MESSAGE_KEY_SEPARATOR = '\u0000';
|
|
|
5
5
|
/** Timeout for session recreation - 1 hour */
|
|
6
6
|
const RECREATE_SESSION_TIMEOUT = 60 * 60 * 1000; // 1 hour in milliseconds
|
|
7
7
|
const PHONE_REQUEST_DELAY = 3000;
|
|
8
|
+
// Retry reason codes matching WhatsApp Web's Signal error codes.
|
|
9
|
+
export var RetryReason;
|
|
10
|
+
(function (RetryReason) {
|
|
11
|
+
RetryReason[RetryReason["UnknownError"] = 0] = "UnknownError";
|
|
12
|
+
RetryReason[RetryReason["SignalErrorNoSession"] = 1] = "SignalErrorNoSession";
|
|
13
|
+
RetryReason[RetryReason["SignalErrorInvalidKey"] = 2] = "SignalErrorInvalidKey";
|
|
14
|
+
RetryReason[RetryReason["SignalErrorInvalidKeyId"] = 3] = "SignalErrorInvalidKeyId";
|
|
15
|
+
/** MAC verification failed - most common cause of decryption failures */
|
|
16
|
+
RetryReason[RetryReason["SignalErrorInvalidMessage"] = 4] = "SignalErrorInvalidMessage";
|
|
17
|
+
RetryReason[RetryReason["SignalErrorInvalidSignature"] = 5] = "SignalErrorInvalidSignature";
|
|
18
|
+
RetryReason[RetryReason["SignalErrorFutureMessage"] = 6] = "SignalErrorFutureMessage";
|
|
19
|
+
/** Explicit MAC failure - session is definitely out of sync */
|
|
20
|
+
RetryReason[RetryReason["SignalErrorBadMac"] = 7] = "SignalErrorBadMac";
|
|
21
|
+
RetryReason[RetryReason["SignalErrorInvalidSession"] = 8] = "SignalErrorInvalidSession";
|
|
22
|
+
RetryReason[RetryReason["SignalErrorInvalidMsgKey"] = 9] = "SignalErrorInvalidMsgKey";
|
|
23
|
+
RetryReason[RetryReason["BadBroadcastEphemeralSetting"] = 10] = "BadBroadcastEphemeralSetting";
|
|
24
|
+
RetryReason[RetryReason["UnknownCompanionNoPrekey"] = 11] = "UnknownCompanionNoPrekey";
|
|
25
|
+
RetryReason[RetryReason["AdvFailure"] = 12] = "AdvFailure";
|
|
26
|
+
RetryReason[RetryReason["StatusRevokeDelay"] = 13] = "StatusRevokeDelay";
|
|
27
|
+
})(RetryReason || (RetryReason = {}));
|
|
28
|
+
/** Error codes that indicate a MAC failure and require immediate session recreation */
|
|
29
|
+
const MAC_ERROR_CODES = new Set([RetryReason.SignalErrorInvalidMessage, RetryReason.SignalErrorBadMac]);
|
|
8
30
|
export class MessageRetryManager {
|
|
9
31
|
constructor(logger, maxMsgRetryCount) {
|
|
10
32
|
this.logger = logger;
|
|
@@ -65,9 +87,10 @@ export class MessageRetryManager {
|
|
|
65
87
|
return this.recentMessagesMap.get(keyStr);
|
|
66
88
|
}
|
|
67
89
|
/**
|
|
68
|
-
* Check if a session should be recreated based on retry count and
|
|
90
|
+
* Check if a session should be recreated based on retry count, history, and error code.
|
|
91
|
+
* MAC errors (codes 4 and 7) trigger immediate session recreation regardless of timeout.
|
|
69
92
|
*/
|
|
70
|
-
shouldRecreateSession(jid,
|
|
93
|
+
shouldRecreateSession(jid, hasSession, errorCode) {
|
|
71
94
|
// If we don't have a session, always recreate
|
|
72
95
|
if (!hasSession) {
|
|
73
96
|
this.sessionRecreateHistory.set(jid, Date.now());
|
|
@@ -77,9 +100,15 @@ export class MessageRetryManager {
|
|
|
77
100
|
recreate: true
|
|
78
101
|
};
|
|
79
102
|
}
|
|
80
|
-
//
|
|
81
|
-
if (
|
|
82
|
-
|
|
103
|
+
// IMMEDIATE recreation for MAC errors - session is definitely out of sync
|
|
104
|
+
if (errorCode !== undefined && MAC_ERROR_CODES.has(errorCode)) {
|
|
105
|
+
this.sessionRecreateHistory.set(jid, Date.now());
|
|
106
|
+
this.statistics.sessionRecreations++;
|
|
107
|
+
this.logger.warn({ jid, errorCode: RetryReason[errorCode] }, 'MAC error detected, forcing immediate session recreation');
|
|
108
|
+
return {
|
|
109
|
+
reason: `MAC error (code ${errorCode}: ${RetryReason[errorCode]}), immediate session recreation`,
|
|
110
|
+
recreate: true
|
|
111
|
+
};
|
|
83
112
|
}
|
|
84
113
|
const now = Date.now();
|
|
85
114
|
const prevTime = this.sessionRecreateHistory.get(jid);
|
|
@@ -94,6 +123,30 @@ export class MessageRetryManager {
|
|
|
94
123
|
}
|
|
95
124
|
return { reason: '', recreate: false };
|
|
96
125
|
}
|
|
126
|
+
/**
|
|
127
|
+
* Parse error code from retry receipt's retry node.
|
|
128
|
+
* Returns undefined if no error code is present.
|
|
129
|
+
*/
|
|
130
|
+
parseRetryErrorCode(errorAttr) {
|
|
131
|
+
if (errorAttr === undefined || errorAttr === '') {
|
|
132
|
+
return undefined;
|
|
133
|
+
}
|
|
134
|
+
const code = parseInt(errorAttr, 10);
|
|
135
|
+
if (Number.isNaN(code)) {
|
|
136
|
+
return undefined;
|
|
137
|
+
}
|
|
138
|
+
// Validate it's a known RetryReason
|
|
139
|
+
if (code >= RetryReason.UnknownError && code <= RetryReason.StatusRevokeDelay) {
|
|
140
|
+
return code;
|
|
141
|
+
}
|
|
142
|
+
return RetryReason.UnknownError;
|
|
143
|
+
}
|
|
144
|
+
/**
|
|
145
|
+
* Check if an error code indicates a MAC failure
|
|
146
|
+
*/
|
|
147
|
+
isMacError(errorCode) {
|
|
148
|
+
return errorCode !== undefined && MAC_ERROR_CODES.has(errorCode);
|
|
149
|
+
}
|
|
97
150
|
/**
|
|
98
151
|
* Increment retry counter for a message
|
|
99
152
|
*/
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"message-retry-manager.js","sourceRoot":"","sources":["../../src/Utils/message-retry-manager.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,WAAW,CAAA;AAIpC,6EAA6E;AAC7E,MAAM,oBAAoB,GAAG,GAAG,CAAA;AAEhC,MAAM,qBAAqB,GAAG,QAAQ,CAAA;AAEtC,8CAA8C;AAC9C,MAAM,wBAAwB,GAAG,EAAE,GAAG,EAAE,GAAG,IAAI,CAAA,CAAC,yBAAyB;AACzE,MAAM,mBAAmB,GAAG,IAAI,CAAA;AA8BhC,MAAM,OAAO,mBAAmB;IAkC/B,YACS,MAAe,EACvB,gBAAwB;QADhB,WAAM,GAAN,MAAM,CAAS;QAlChB,sBAAiB,GAAG,IAAI,QAAQ,CAAwB;YAC/D,GAAG,EAAE,oBAAoB;YACzB,GAAG,EAAE,CAAC,GAAG,EAAE,GAAG,IAAI;YAClB,YAAY,EAAE,IAAI;YAClB,OAAO,EAAE,CAAC,MAAqB,EAAE,GAAW,EAAE,EAAE;gBAC/C,MAAM,cAAc,GAAG,GAAG,CAAC,WAAW,CAAC,qBAAqB,CAAC,CAAA;gBAC7D,IAAI,cAAc,GAAG,CAAC,CAAC,EAAE,CAAC;oBACzB,MAAM,SAAS,GAAG,GAAG,CAAC,KAAK,CAAC,cAAc,GAAG,qBAAqB,CAAC,MAAM,CAAC,CAAA;oBAC1E,IAAI,CAAC,eAAe,CAAC,MAAM,CAAC,SAAS,CAAC,CAAA;gBACvC,CAAC;YACF,CAAC;SACD,CAAC,CAAA;QACM,oBAAe,GAAG,IAAI,GAAG,EAAkB,CAAA;QAC3C,2BAAsB,GAAG,IAAI,QAAQ,CAAiB;YAC7D,GAAG,EAAE,wBAAwB,GAAG,CAAC;YACjC,YAAY,EAAE,IAAI;SAClB,CAAC,CAAA;QACM,kBAAa,GAAG,IAAI,QAAQ,CAAiB;YACpD,GAAG,EAAE,EAAE,GAAG,EAAE,GAAG,IAAI;YACnB,YAAY,EAAE,IAAI;YAClB,cAAc,EAAE,IAAI;SACpB,CAAC,CAAA,CAAC,iBAAiB;QACZ,yBAAoB,GAAwB,EAAE,CAAA;QACrC,qBAAgB,GAAW,CAAC,CAAA;QACrC,eAAU,GAAoB;YACrC,YAAY,EAAE,CAAC;YACf,iBAAiB,EAAE,CAAC;YACpB,aAAa,EAAE,CAAC;YAChB,YAAY,EAAE,CAAC;YACf,kBAAkB,EAAE,CAAC;YACrB,aAAa,EAAE,CAAC;SAChB,CAAA;QAMA,IAAI,CAAC,gBAAgB,GAAG,gBAAgB,CAAA;IACzC,CAAC;IAED;;OAEG;IACH,gBAAgB,CAAC,EAAU,EAAE,EAAU,EAAE,OAAuB;QAC/D,MAAM,GAAG,GAAqB,EAAE,EAAE,EAAE,EAAE,EAAE,CAAA;QACxC,MAAM,MAAM,GAAG,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,CAAA;QAEpC,kBAAkB;QAClB,IAAI,CAAC,iBAAiB,CAAC,GAAG,CAAC,MAAM,EAAE;YAClC,OAAO;YACP,SAAS,EAAE,IAAI,CAAC,GAAG,EAAE;SACrB,CAAC,CAAA;QACF,IAAI,CAAC,eAAe,CAAC,GAAG,CAAC,EAAE,EAAE,MAAM,CAAC,CAAA;QAEpC,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,iCAAiC,EAAE,IAAI,EAAE,EAAE,CAAC,CAAA;IAC/D,CAAC;IAED;;OAEG;IACH,gBAAgB,CAAC,EAAU,EAAE,EAAU;QACtC,MAAM,GAAG,GAAqB,EAAE,EAAE,EAAE,EAAE,EAAE,CAAA;QACxC,MAAM,MAAM,GAAG,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC,CAAA;QACpC,OAAO,IAAI,CAAC,iBAAiB,CAAC,GAAG,CAAC,MAAM,CAAC,CAAA;IAC1C,CAAC;IAED
|
|
1
|
+
{"version":3,"file":"message-retry-manager.js","sourceRoot":"","sources":["../../src/Utils/message-retry-manager.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { Boom } from '@hapi/boom';
|
|
2
|
+
import type { Agent } from 'https';
|
|
2
3
|
import { Readable, Transform } from 'stream';
|
|
3
4
|
import { URL } from 'url';
|
|
4
5
|
import { proto } from '../../WAProto/index.js';
|
|
@@ -6,6 +7,13 @@ import { type MediaType } from '../Defaults/index.js';
|
|
|
6
7
|
import type { DownloadableMessage, MediaConnInfo, MediaDecryptionKeyInfo, SocketConfig, WAMediaUpload, WAMediaUploadFunction, WAMessageContent, WAMessageKey } from '../Types/index.js';
|
|
7
8
|
import { type BinaryNode } from '../WABinary/index.js';
|
|
8
9
|
import type { ILogger } from './logger.js';
|
|
10
|
+
export declare const getImageProcessingLibrary: () => Promise<{
|
|
11
|
+
sharp: any;
|
|
12
|
+
jimp?: undefined;
|
|
13
|
+
} | {
|
|
14
|
+
jimp: typeof import("jimp");
|
|
15
|
+
sharp?: undefined;
|
|
16
|
+
}>;
|
|
9
17
|
export declare const hkdfInfoKey: (type: MediaType) => string;
|
|
10
18
|
export declare const getRawMediaUploadData: (media: WAMediaUpload, mediaType: MediaType, logger?: ILogger) => Promise<{
|
|
11
19
|
filePath: string;
|
|
@@ -55,6 +63,7 @@ export declare const getStream: (item: WAMediaUpload, opts?: RequestInit & {
|
|
|
55
63
|
/** generates a thumbnail for a given media, if required */
|
|
56
64
|
export declare function generateThumbnail(file: string, mediaType: 'video' | 'image', options: {
|
|
57
65
|
logger?: ILogger;
|
|
66
|
+
hdMode?: boolean;
|
|
58
67
|
}): Promise<{
|
|
59
68
|
thumbnail: string | undefined;
|
|
60
69
|
originalImageDimensions: {
|
|
@@ -69,9 +78,11 @@ type EncryptedStreamOptions = {
|
|
|
69
78
|
saveOriginalFileIfRequired?: boolean;
|
|
70
79
|
logger?: ILogger;
|
|
71
80
|
opts?: RequestInit;
|
|
81
|
+
/** Optional mediaKey to reuse (required for sticker pack thumbnail to match ZIP encryption) */
|
|
82
|
+
mediaKey?: Buffer | Uint8Array;
|
|
72
83
|
};
|
|
73
|
-
export declare const encryptedStream: (media: WAMediaUpload, mediaType: MediaType, { logger, saveOriginalFileIfRequired, opts }?: EncryptedStreamOptions) => Promise<{
|
|
74
|
-
mediaKey:
|
|
84
|
+
export declare const encryptedStream: (media: WAMediaUpload, mediaType: MediaType, { logger, saveOriginalFileIfRequired, opts, mediaKey: providedMediaKey }?: EncryptedStreamOptions) => Promise<{
|
|
85
|
+
mediaKey: Buffer<ArrayBuffer>;
|
|
75
86
|
originalFilePath: string | undefined;
|
|
76
87
|
encFilePath: string;
|
|
77
88
|
mac: Buffer<ArrayBuffer>;
|
|
@@ -92,11 +103,30 @@ export declare const downloadContentFromMessage: ({ mediaKey, directPath, url }:
|
|
|
92
103
|
* */
|
|
93
104
|
export declare const downloadEncryptedContent: (downloadUrl: string, { cipherKey, iv }: MediaDecryptionKeyInfo, { startByte, endByte, options }?: MediaDownloadOptions) => Promise<Transform>;
|
|
94
105
|
export declare function extensionForMediaMessage(message: WAMessageContent): string;
|
|
106
|
+
type MediaUploadResult = {
|
|
107
|
+
url?: string;
|
|
108
|
+
direct_path?: string;
|
|
109
|
+
meta_hmac?: string;
|
|
110
|
+
ts?: number;
|
|
111
|
+
fbid?: number;
|
|
112
|
+
thumbnail_info?: {
|
|
113
|
+
thumbnail_sha256?: string;
|
|
114
|
+
thumbnail_direct_path?: string;
|
|
115
|
+
};
|
|
116
|
+
};
|
|
117
|
+
export type UploadParams = {
|
|
118
|
+
url: string;
|
|
119
|
+
filePath: string;
|
|
120
|
+
headers: Record<string, string>;
|
|
121
|
+
timeoutMs?: number;
|
|
122
|
+
agent?: Agent;
|
|
123
|
+
};
|
|
124
|
+
export declare const uploadWithNodeHttp: ({ url, filePath, headers, timeoutMs, agent }: UploadParams, redirectCount?: number) => Promise<MediaUploadResult | undefined>;
|
|
95
125
|
export declare const getWAUploadToServer: ({ customUploadHosts, fetchAgent, logger, options }: SocketConfig, refreshMediaConn: (force: boolean) => Promise<MediaConnInfo>) => WAMediaUploadFunction;
|
|
96
126
|
/**
|
|
97
127
|
* Generate a binary node that will request the phone to re-upload the media & return the newly uploaded URL
|
|
98
128
|
*/
|
|
99
|
-
export declare const encryptMediaRetryRequest: (key: WAMessageKey, mediaKey: Buffer | Uint8Array, meId: string) =>
|
|
129
|
+
export declare const encryptMediaRetryRequest: (key: WAMessageKey, mediaKey: Buffer | Uint8Array, meId: string) => BinaryNode;
|
|
100
130
|
export declare const decodeMediaRetryNode: (node: BinaryNode) => {
|
|
101
131
|
key: WAMessageKey;
|
|
102
132
|
media?: {
|
|
@@ -108,7 +138,7 @@ export declare const decodeMediaRetryNode: (node: BinaryNode) => {
|
|
|
108
138
|
export declare const decryptMediaRetryData: ({ ciphertext, iv }: {
|
|
109
139
|
ciphertext: Uint8Array;
|
|
110
140
|
iv: Uint8Array;
|
|
111
|
-
}, mediaKey: Uint8Array, msgId: string) =>
|
|
112
|
-
export declare const getStatusCodeForMediaRetry: (code: number) =>
|
|
141
|
+
}, mediaKey: Uint8Array, msgId: string) => proto.MediaRetryNotification;
|
|
142
|
+
export declare const getStatusCodeForMediaRetry: (code: number) => number | undefined;
|
|
113
143
|
export {};
|
|
114
144
|
//# sourceMappingURL=messages-media.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"messages-media.d.ts","sourceRoot":"","sources":["../../src/Utils/messages-media.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,YAAY,CAAA;
|
|
1
|
+
{"version":3,"file":"messages-media.d.ts","sourceRoot":"","sources":["../../src/Utils/messages-media.ts"],"names":[],"mappings":"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"}
|
|
@@ -8,12 +8,12 @@ import { join } from 'path';
|
|
|
8
8
|
import { Readable, Transform } from 'stream';
|
|
9
9
|
import { URL } from 'url';
|
|
10
10
|
import { proto } from '../../WAProto/index.js';
|
|
11
|
-
import { DEFAULT_ORIGIN, MEDIA_HKDF_KEY_MAPPING, MEDIA_PATH_MAP } from '../Defaults/index.js';
|
|
11
|
+
import { DEFAULT_ORIGIN, MEDIA_HKDF_KEY_MAPPING, MEDIA_PATH_MAP, NEWSLETTER_MEDIA_PATH_MAP } from '../Defaults/index.js';
|
|
12
12
|
import { getBinaryNodeChild, getBinaryNodeChildBuffer, jidNormalizedUser } from '../WABinary/index.js';
|
|
13
13
|
import { aesDecryptGCM, aesEncryptGCM, hkdf } from './crypto.js';
|
|
14
14
|
import { generateMessageIDV2 } from './generics.js';
|
|
15
15
|
const getTmpFilesDirectory = () => tmpdir();
|
|
16
|
-
const getImageProcessingLibrary = async () => {
|
|
16
|
+
export const getImageProcessingLibrary = async () => {
|
|
17
17
|
//@ts-ignore
|
|
18
18
|
const [jimp, sharp] = await Promise.all([import('jimp').catch(() => { }), import('sharp').catch(() => { })]);
|
|
19
19
|
if (sharp) {
|
|
@@ -75,7 +75,7 @@ export async function getMediaKeys(buffer, mediaType) {
|
|
|
75
75
|
buffer = Buffer.from(buffer.replace('data:;base64,', ''), 'base64');
|
|
76
76
|
}
|
|
77
77
|
// expand using HKDF to 112 bytes, also pass in the relevant app info
|
|
78
|
-
const expandedMediaKey =
|
|
78
|
+
const expandedMediaKey = hkdf(buffer, 112, { info: hkdfInfoKey(mediaType) });
|
|
79
79
|
return {
|
|
80
80
|
iv: expandedMediaKey.slice(0, 16),
|
|
81
81
|
cipherKey: expandedMediaKey.slice(16, 48),
|
|
@@ -267,8 +267,9 @@ export const getStream = async (item, opts) => {
|
|
|
267
267
|
export async function generateThumbnail(file, mediaType, options) {
|
|
268
268
|
let thumbnail;
|
|
269
269
|
let originalImageDimensions;
|
|
270
|
+
const hdMode = options.hdMode === true;
|
|
270
271
|
if (mediaType === 'image') {
|
|
271
|
-
const { buffer, original } = await extractImageThumb(file);
|
|
272
|
+
const { buffer, original } = await extractImageThumb(file, hdMode ? 320 : undefined);
|
|
272
273
|
thumbnail = buffer.toString('base64');
|
|
273
274
|
if (original.width && original.height) {
|
|
274
275
|
originalImageDimensions = {
|
|
@@ -278,9 +279,10 @@ export async function generateThumbnail(file, mediaType, options) {
|
|
|
278
279
|
}
|
|
279
280
|
}
|
|
280
281
|
else if (mediaType === 'video') {
|
|
282
|
+
const thumbSize = hdMode ? { width: 320, height: 180 } : { width: 32, height: 32 };
|
|
281
283
|
const imgFilename = join(getTmpFilesDirectory(), generateMessageIDV2() + '.jpg');
|
|
282
284
|
try {
|
|
283
|
-
await extractVideoThumb(file, imgFilename, '00:00:00',
|
|
285
|
+
await extractVideoThumb(file, imgFilename, '00:00:00', thumbSize);
|
|
284
286
|
const buff = await fs.readFile(imgFilename);
|
|
285
287
|
thumbnail = buff.toString('base64');
|
|
286
288
|
await fs.unlink(imgFilename);
|
|
@@ -306,10 +308,10 @@ export const getHttpStream = async (url, options = {}) => {
|
|
|
306
308
|
// @ts-ignore Node18+ Readable.fromWeb exists
|
|
307
309
|
return response.body instanceof Readable ? response.body : Readable.fromWeb(response.body);
|
|
308
310
|
};
|
|
309
|
-
export const encryptedStream = async (media, mediaType, { logger, saveOriginalFileIfRequired, opts } = {}) => {
|
|
311
|
+
export const encryptedStream = async (media, mediaType, { logger, saveOriginalFileIfRequired, opts, mediaKey: providedMediaKey } = {}) => {
|
|
310
312
|
const { stream, type } = await getStream(media, opts);
|
|
311
313
|
logger?.debug('fetched media stream');
|
|
312
|
-
const mediaKey = Crypto.randomBytes(32);
|
|
314
|
+
const mediaKey = providedMediaKey ? Buffer.from(providedMediaKey) : Crypto.randomBytes(32);
|
|
313
315
|
const { cipherKey, iv, macKey } = await getMediaKeys(mediaKey, mediaType);
|
|
314
316
|
const encFilePath = join(getTmpFilesDirectory(), mediaType + generateMessageIDV2() + '-enc');
|
|
315
317
|
const encFileWriteStream = createWriteStream(encFilePath);
|
|
@@ -324,10 +326,13 @@ export const encryptedStream = async (media, mediaType, { logger, saveOriginalFi
|
|
|
324
326
|
const hmac = Crypto.createHmac('sha256', macKey).update(iv);
|
|
325
327
|
const sha256Plain = Crypto.createHash('sha256');
|
|
326
328
|
const sha256Enc = Crypto.createHash('sha256');
|
|
327
|
-
const onChunk = (buff) => {
|
|
329
|
+
const onChunk = async (buff) => {
|
|
328
330
|
sha256Enc.update(buff);
|
|
329
331
|
hmac.update(buff);
|
|
330
|
-
|
|
332
|
+
// Handle backpressure: if write returns false, wait for drain
|
|
333
|
+
if (!encFileWriteStream.write(buff)) {
|
|
334
|
+
await once(encFileWriteStream, 'drain');
|
|
335
|
+
}
|
|
331
336
|
};
|
|
332
337
|
try {
|
|
333
338
|
for await (const data of stream) {
|
|
@@ -345,17 +350,23 @@ export const encryptedStream = async (media, mediaType, { logger, saveOriginalFi
|
|
|
345
350
|
}
|
|
346
351
|
}
|
|
347
352
|
sha256Plain.update(data);
|
|
348
|
-
onChunk(aes.update(data));
|
|
353
|
+
await onChunk(aes.update(data));
|
|
349
354
|
}
|
|
350
|
-
onChunk(aes.final());
|
|
355
|
+
await onChunk(aes.final());
|
|
351
356
|
const mac = hmac.digest().slice(0, 10);
|
|
352
357
|
sha256Enc.update(mac);
|
|
353
358
|
const fileSha256 = sha256Plain.digest();
|
|
354
359
|
const fileEncSha256 = sha256Enc.digest();
|
|
355
360
|
encFileWriteStream.write(mac);
|
|
361
|
+
const encFinishPromise = once(encFileWriteStream, 'finish');
|
|
362
|
+
const originalFinishPromise = originalFileStream ? once(originalFileStream, 'finish') : Promise.resolve();
|
|
356
363
|
encFileWriteStream.end();
|
|
357
364
|
originalFileStream?.end?.();
|
|
358
365
|
stream.destroy();
|
|
366
|
+
// Wait for write streams to fully flush to disk
|
|
367
|
+
// This helps reduce memory pressure by allowing OS to release buffers
|
|
368
|
+
await encFinishPromise;
|
|
369
|
+
await originalFinishPromise;
|
|
359
370
|
logger?.debug('encrypted data successfully');
|
|
360
371
|
return {
|
|
361
372
|
mediaKey,
|
|
@@ -456,7 +467,7 @@ export const downloadEncryptedContent = async (downloadUrl, { cipherKey, iv }, {
|
|
|
456
467
|
};
|
|
457
468
|
const output = new Transform({
|
|
458
469
|
transform(chunk, _, callback) {
|
|
459
|
-
let data = Buffer.concat([remainingBytes, chunk]);
|
|
470
|
+
let data = remainingBytes.length ? Buffer.concat([remainingBytes, chunk]) : chunk;
|
|
460
471
|
const decryptLength = toSmallestChunkSize(data.length);
|
|
461
472
|
remainingBytes = data.slice(decryptLength);
|
|
462
473
|
data = data.slice(0, decryptLength);
|
|
@@ -506,54 +517,163 @@ export function extensionForMediaMessage(message) {
|
|
|
506
517
|
}
|
|
507
518
|
return extension;
|
|
508
519
|
}
|
|
520
|
+
const isNodeRuntime = () => {
|
|
521
|
+
return (typeof process !== 'undefined' &&
|
|
522
|
+
process.versions?.node !== null &&
|
|
523
|
+
typeof process.versions.bun === 'undefined' &&
|
|
524
|
+
typeof globalThis.Deno === 'undefined');
|
|
525
|
+
};
|
|
526
|
+
export const uploadWithNodeHttp = async ({ url, filePath, headers, timeoutMs, agent }, redirectCount = 0) => {
|
|
527
|
+
if (redirectCount > 5) {
|
|
528
|
+
throw new Error('Too many redirects');
|
|
529
|
+
}
|
|
530
|
+
const parsedUrl = new URL(url);
|
|
531
|
+
const httpModule = parsedUrl.protocol === 'https:' ? await import('https') : await import('http');
|
|
532
|
+
// Get file size for Content-Length header (required for Node.js streaming)
|
|
533
|
+
const fileStats = await fs.stat(filePath);
|
|
534
|
+
const fileSize = fileStats.size;
|
|
535
|
+
return new Promise((resolve, reject) => {
|
|
536
|
+
const req = httpModule.request({
|
|
537
|
+
hostname: parsedUrl.hostname,
|
|
538
|
+
port: parsedUrl.port || (parsedUrl.protocol === 'https:' ? 443 : 80),
|
|
539
|
+
path: parsedUrl.pathname + parsedUrl.search,
|
|
540
|
+
method: 'POST',
|
|
541
|
+
headers: {
|
|
542
|
+
...headers,
|
|
543
|
+
'Content-Length': fileSize
|
|
544
|
+
},
|
|
545
|
+
agent,
|
|
546
|
+
timeout: timeoutMs
|
|
547
|
+
}, res => {
|
|
548
|
+
// Handle redirects (3xx)
|
|
549
|
+
if (res.statusCode && res.statusCode >= 300 && res.statusCode < 400 && res.headers.location) {
|
|
550
|
+
res.resume(); // Consume response to free resources
|
|
551
|
+
const newUrl = new URL(res.headers.location, url).toString();
|
|
552
|
+
resolve(uploadWithNodeHttp({
|
|
553
|
+
url: newUrl,
|
|
554
|
+
filePath,
|
|
555
|
+
headers,
|
|
556
|
+
timeoutMs,
|
|
557
|
+
agent
|
|
558
|
+
}, redirectCount + 1));
|
|
559
|
+
return;
|
|
560
|
+
}
|
|
561
|
+
let body = '';
|
|
562
|
+
res.on('data', chunk => (body += chunk));
|
|
563
|
+
res.on('end', () => {
|
|
564
|
+
try {
|
|
565
|
+
resolve(JSON.parse(body));
|
|
566
|
+
}
|
|
567
|
+
catch {
|
|
568
|
+
resolve(undefined);
|
|
569
|
+
}
|
|
570
|
+
});
|
|
571
|
+
});
|
|
572
|
+
req.on('error', reject);
|
|
573
|
+
req.on('timeout', () => {
|
|
574
|
+
req.destroy();
|
|
575
|
+
reject(new Error('Upload timeout'));
|
|
576
|
+
});
|
|
577
|
+
const stream = createReadStream(filePath);
|
|
578
|
+
stream.pipe(req);
|
|
579
|
+
stream.on('error', err => {
|
|
580
|
+
req.destroy();
|
|
581
|
+
reject(err);
|
|
582
|
+
});
|
|
583
|
+
});
|
|
584
|
+
};
|
|
585
|
+
const uploadWithFetch = async ({ url, filePath, headers, timeoutMs, agent }) => {
|
|
586
|
+
// Convert Node.js Readable to Web ReadableStream
|
|
587
|
+
const nodeStream = createReadStream(filePath);
|
|
588
|
+
const webStream = Readable.toWeb(nodeStream);
|
|
589
|
+
const response = await fetch(url, {
|
|
590
|
+
dispatcher: agent,
|
|
591
|
+
method: 'POST',
|
|
592
|
+
body: webStream,
|
|
593
|
+
headers,
|
|
594
|
+
duplex: 'half',
|
|
595
|
+
signal: timeoutMs ? AbortSignal.timeout(timeoutMs) : undefined
|
|
596
|
+
});
|
|
597
|
+
try {
|
|
598
|
+
return (await response.json());
|
|
599
|
+
}
|
|
600
|
+
catch {
|
|
601
|
+
return undefined;
|
|
602
|
+
}
|
|
603
|
+
};
|
|
604
|
+
/**
|
|
605
|
+
* Uploads media to WhatsApp servers.
|
|
606
|
+
*
|
|
607
|
+
* ## Why we have two upload implementations:
|
|
608
|
+
*
|
|
609
|
+
* Node.js's native `fetch` (powered by undici) has a known bug where it buffers
|
|
610
|
+
* the entire request body in memory before sending, even when using streams.
|
|
611
|
+
* This causes memory issues with large files (e.g., 1GB file = 1GB+ memory usage).
|
|
612
|
+
* See: https://github.com/nodejs/undici/issues/4058
|
|
613
|
+
*
|
|
614
|
+
* Other runtimes (Bun, Deno, browsers) correctly stream the request body without
|
|
615
|
+
* buffering, so we can use the web-standard Fetch API there.
|
|
616
|
+
*
|
|
617
|
+
* ## Future considerations:
|
|
618
|
+
* Once the undici bug is fixed, we can simplify this to use only the Fetch API
|
|
619
|
+
* across all runtimes. Monitor the GitHub issue for updates.
|
|
620
|
+
*/
|
|
621
|
+
const uploadMedia = async (params, logger) => {
|
|
622
|
+
if (isNodeRuntime()) {
|
|
623
|
+
logger?.debug('Using Node.js https module for upload (avoids undici buffering bug)');
|
|
624
|
+
return uploadWithNodeHttp(params);
|
|
625
|
+
}
|
|
626
|
+
else {
|
|
627
|
+
logger?.debug('Using web-standard Fetch API for upload');
|
|
628
|
+
return uploadWithFetch(params);
|
|
629
|
+
}
|
|
630
|
+
};
|
|
509
631
|
export const getWAUploadToServer = ({ customUploadHosts, fetchAgent, logger, options }, refreshMediaConn) => {
|
|
510
|
-
return async (filePath, { mediaType, fileEncSha256B64, timeoutMs }) => {
|
|
632
|
+
return async (filePath, { mediaType, fileEncSha256B64, timeoutMs, newsletter }) => {
|
|
511
633
|
// send a query JSON to obtain the url & auth token to upload our media
|
|
512
634
|
let uploadInfo = await refreshMediaConn(false);
|
|
513
635
|
let urls;
|
|
514
636
|
const hosts = [...customUploadHosts, ...uploadInfo.hosts];
|
|
515
637
|
fileEncSha256B64 = encodeBase64EncodedStringForUpload(fileEncSha256B64);
|
|
638
|
+
// Prepare common headers
|
|
639
|
+
const customHeaders = (() => {
|
|
640
|
+
const hdrs = options?.headers;
|
|
641
|
+
if (!hdrs)
|
|
642
|
+
return {};
|
|
643
|
+
return Array.isArray(hdrs) ? Object.fromEntries(hdrs) : hdrs;
|
|
644
|
+
})();
|
|
645
|
+
const headers = {
|
|
646
|
+
...customHeaders,
|
|
647
|
+
'Content-Type': 'application/octet-stream',
|
|
648
|
+
Origin: DEFAULT_ORIGIN
|
|
649
|
+
};
|
|
516
650
|
for (const { hostname } of hosts) {
|
|
517
651
|
logger.debug(`uploading to "${hostname}"`);
|
|
518
|
-
const auth = encodeURIComponent(uploadInfo.auth);
|
|
519
|
-
|
|
520
|
-
|
|
652
|
+
const auth = encodeURIComponent(uploadInfo.auth);
|
|
653
|
+
// Use newsletter-specific path when uploading for a newsletter/channel
|
|
654
|
+
const mediaPath = (newsletter ? NEWSLETTER_MEDIA_PATH_MAP[mediaType] : undefined) || MEDIA_PATH_MAP[mediaType];
|
|
655
|
+
let url = `https://${hostname}${mediaPath}/${fileEncSha256B64}?auth=${auth}&token=${fileEncSha256B64}`;
|
|
656
|
+
if (newsletter) {
|
|
657
|
+
url += '&server_thumb_gen=1';
|
|
658
|
+
}
|
|
521
659
|
let result;
|
|
522
660
|
try {
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
|
|
529
|
-
|
|
530
|
-
|
|
531
|
-
if (!hdrs)
|
|
532
|
-
return {};
|
|
533
|
-
return Array.isArray(hdrs) ? Object.fromEntries(hdrs) : hdrs;
|
|
534
|
-
})(),
|
|
535
|
-
'Content-Type': 'application/octet-stream',
|
|
536
|
-
Origin: DEFAULT_ORIGIN
|
|
537
|
-
},
|
|
538
|
-
duplex: 'half',
|
|
539
|
-
// Note: custom agents/proxy require undici Agent; omitted here.
|
|
540
|
-
signal: timeoutMs ? AbortSignal.timeout(timeoutMs) : undefined
|
|
541
|
-
});
|
|
542
|
-
let parsed = undefined;
|
|
543
|
-
try {
|
|
544
|
-
parsed = await response.json();
|
|
545
|
-
}
|
|
546
|
-
catch {
|
|
547
|
-
parsed = undefined;
|
|
548
|
-
}
|
|
549
|
-
result = parsed;
|
|
550
|
-
if (result?.url || result?.directPath) {
|
|
661
|
+
result = await uploadMedia({
|
|
662
|
+
url,
|
|
663
|
+
filePath,
|
|
664
|
+
headers,
|
|
665
|
+
timeoutMs,
|
|
666
|
+
agent: fetchAgent
|
|
667
|
+
}, logger);
|
|
668
|
+
if (result?.url || result?.direct_path) {
|
|
551
669
|
urls = {
|
|
552
|
-
mediaUrl: result.url,
|
|
670
|
+
mediaUrl: result.url || result.direct_path,
|
|
553
671
|
directPath: result.direct_path,
|
|
554
672
|
meta_hmac: result.meta_hmac,
|
|
555
673
|
fbid: result.fbid,
|
|
556
|
-
ts: result.ts
|
|
674
|
+
ts: result.ts,
|
|
675
|
+
thumbnailDirectPath: result.thumbnail_info?.thumbnail_direct_path,
|
|
676
|
+
thumbnailSha256: result.thumbnail_info?.thumbnail_sha256
|
|
557
677
|
};
|
|
558
678
|
break;
|
|
559
679
|
}
|
|
@@ -579,11 +699,11 @@ const getMediaRetryKey = (mediaKey) => {
|
|
|
579
699
|
/**
|
|
580
700
|
* Generate a binary node that will request the phone to re-upload the media & return the newly uploaded URL
|
|
581
701
|
*/
|
|
582
|
-
export const encryptMediaRetryRequest =
|
|
702
|
+
export const encryptMediaRetryRequest = (key, mediaKey, meId) => {
|
|
583
703
|
const recp = { stanzaId: key.id };
|
|
584
704
|
const recpBuffer = proto.ServerErrorReceipt.encode(recp).finish();
|
|
585
705
|
const iv = Crypto.randomBytes(12);
|
|
586
|
-
const retryKey =
|
|
706
|
+
const retryKey = getMediaRetryKey(mediaKey);
|
|
587
707
|
const ciphertext = aesEncryptGCM(recpBuffer, retryKey, iv, Buffer.from(key.id));
|
|
588
708
|
const req = {
|
|
589
709
|
tag: 'receipt',
|
|
@@ -648,16 +768,16 @@ export const decodeMediaRetryNode = (node) => {
|
|
|
648
768
|
}
|
|
649
769
|
return event;
|
|
650
770
|
};
|
|
651
|
-
export const decryptMediaRetryData =
|
|
652
|
-
const retryKey =
|
|
771
|
+
export const decryptMediaRetryData = ({ ciphertext, iv }, mediaKey, msgId) => {
|
|
772
|
+
const retryKey = getMediaRetryKey(mediaKey);
|
|
653
773
|
const plaintext = aesDecryptGCM(ciphertext, retryKey, iv, Buffer.from(msgId));
|
|
654
774
|
return proto.MediaRetryNotification.decode(plaintext);
|
|
655
775
|
};
|
|
656
|
-
export const getStatusCodeForMediaRetry = (code) => MEDIA_RETRY_STATUS_MAP[code];
|
|
657
776
|
const MEDIA_RETRY_STATUS_MAP = {
|
|
658
777
|
[proto.MediaRetryNotification.ResultType.SUCCESS]: 200,
|
|
659
778
|
[proto.MediaRetryNotification.ResultType.DECRYPTION_ERROR]: 412,
|
|
660
779
|
[proto.MediaRetryNotification.ResultType.NOT_FOUND]: 404,
|
|
661
780
|
[proto.MediaRetryNotification.ResultType.GENERAL_ERROR]: 418
|
|
662
781
|
};
|
|
782
|
+
export const getStatusCodeForMediaRetry = (code) => MEDIA_RETRY_STATUS_MAP[code];
|
|
663
783
|
//# sourceMappingURL=messages-media.js.map
|