@japofc/baileys 2.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/NOTICE.md +111 -0
- package/README.md +1254 -0
- package/WAProto/index.d.ts +9 -0
- package/WAProto/index.js +142276 -0
- package/engine-requirements.js +13 -0
- package/lib/Builders/A2UI.d.ts +242 -0
- package/lib/Builders/A2UI.js +308 -0
- package/lib/Builders/AIRich.d.ts +105 -0
- package/lib/Builders/AIRich.js +2286 -0
- package/lib/Builders/Button.d.ts +103 -0
- package/lib/Builders/Button.js +883 -0
- package/lib/Builders/ButtonV2.d.ts +28 -0
- package/lib/Builders/ButtonV2.js +144 -0
- package/lib/Builders/ButtonV3.d.ts +25 -0
- package/lib/Builders/ButtonV3.js +184 -0
- package/lib/Builders/Carousel.d.ts +22 -0
- package/lib/Builders/Carousel.js +111 -0
- package/lib/Builders/JapBaileys.d.ts +34 -0
- package/lib/Builders/JapBaileys.js +108 -0
- package/lib/Builders/Poll.d.ts +25 -0
- package/lib/Builders/Poll.js +128 -0
- package/lib/Builders/index.d.ts +17 -0
- package/lib/Builders/index.js +11 -0
- package/lib/Builders/shared.d.ts +67 -0
- package/lib/Builders/shared.js +652 -0
- package/lib/Defaults/index.d.ts +154 -0
- package/lib/Defaults/index.js +178 -0
- package/lib/Framework/Bot.d.ts +61 -0
- package/lib/Framework/Bot.js +248 -0
- package/lib/Framework/Context.d.ts +21 -0
- package/lib/Framework/Context.js +89 -0
- package/lib/Framework/MediaManager.d.ts +17 -0
- package/lib/Framework/MediaManager.js +151 -0
- package/lib/Framework/SessionManager.d.ts +13 -0
- package/lib/Framework/SessionManager.js +33 -0
- package/lib/Framework/StatsManager.d.ts +26 -0
- package/lib/Framework/StatsManager.js +119 -0
- package/lib/Framework/Store/SQLiteStore.d.ts +11 -0
- package/lib/Framework/Store/SQLiteStore.js +73 -0
- package/lib/Framework/index.d.ts +9 -0
- package/lib/Framework/index.js +10 -0
- package/lib/Signal/Group/ciphertext-message.d.ts +9 -0
- package/lib/Signal/Group/ciphertext-message.js +11 -0
- package/lib/Signal/Group/group-session-builder.d.ts +7 -0
- package/lib/Signal/Group/group-session-builder.js +29 -0
- package/lib/Signal/Group/group_cipher.d.ts +10 -0
- package/lib/Signal/Group/group_cipher.js +81 -0
- package/lib/Signal/Group/index.d.ts +11 -0
- package/lib/Signal/Group/index.js +11 -0
- package/lib/Signal/Group/keyhelper.d.ts +6 -0
- package/lib/Signal/Group/keyhelper.js +17 -0
- package/lib/Signal/Group/sender-chain-key.d.ts +13 -0
- package/lib/Signal/Group/sender-chain-key.js +25 -0
- package/lib/Signal/Group/sender-key-distribution-message.d.ts +16 -0
- package/lib/Signal/Group/sender-key-distribution-message.js +62 -0
- package/lib/Signal/Group/sender-key-message.d.ts +18 -0
- package/lib/Signal/Group/sender-key-message.js +65 -0
- package/lib/Signal/Group/sender-key-name.d.ts +11 -0
- package/lib/Signal/Group/sender-key-name.js +47 -0
- package/lib/Signal/Group/sender-key-record.d.ts +12 -0
- package/lib/Signal/Group/sender-key-record.js +40 -0
- package/lib/Signal/Group/sender-key-state.d.ts +16 -0
- package/lib/Signal/Group/sender-key-state.js +83 -0
- package/lib/Signal/Group/sender-message-key.d.ts +11 -0
- package/lib/Signal/Group/sender-message-key.js +25 -0
- package/lib/Signal/libsignal.d.ts +54 -0
- package/lib/Signal/libsignal.js +430 -0
- package/lib/Signal/lid-mapping.d.ts +20 -0
- package/lib/Signal/lid-mapping.js +276 -0
- package/lib/Socket/Client/index.d.ts +2 -0
- package/lib/Socket/Client/index.js +2 -0
- package/lib/Socket/Client/types.d.ts +5 -0
- package/lib/Socket/Client/types.js +10 -0
- package/lib/Socket/Client/websocket.d.ts +12 -0
- package/lib/Socket/Client/websocket.js +53 -0
- package/lib/Socket/business.d.ts +395 -0
- package/lib/Socket/business.js +379 -0
- package/lib/Socket/chats.d.ts +136 -0
- package/lib/Socket/chats.js +1327 -0
- package/lib/Socket/communities.d.ts +562 -0
- package/lib/Socket/communities.js +439 -0
- package/lib/Socket/dugong.d.ts +117 -0
- package/lib/Socket/dugong.js +798 -0
- package/lib/Socket/groups.d.ts +285 -0
- package/lib/Socket/groups.js +354 -0
- package/lib/Socket/index.d.ts +585 -0
- package/lib/Socket/index.js +52 -0
- package/lib/Socket/messages-recv.d.ts +333 -0
- package/lib/Socket/messages-recv.js +1781 -0
- package/lib/Socket/messages-send.d.ts +353 -0
- package/lib/Socket/messages-send.js +1524 -0
- package/lib/Socket/mex.d.ts +1 -0
- package/lib/Socket/mex.js +41 -0
- package/lib/Socket/newsletter.d.ts +286 -0
- package/lib/Socket/newsletter.js +364 -0
- package/lib/Socket/socket.d.ts +60 -0
- package/lib/Socket/socket.js +1012 -0
- package/lib/Socket/username.d.ts +82 -0
- package/lib/Socket/username.js +159 -0
- package/lib/Store/index.d.ts +3 -0
- package/lib/Store/index.js +3 -0
- package/lib/Store/make-in-memory-store.d.ts +62 -0
- package/lib/Store/make-in-memory-store.js +428 -0
- package/lib/Store/make-ordered-dictionary.d.ts +12 -0
- package/lib/Store/make-ordered-dictionary.js +78 -0
- package/lib/Store/object-repository.d.ts +10 -0
- package/lib/Store/object-repository.js +23 -0
- package/lib/Types/Auth.d.ts +117 -0
- package/lib/Types/Auth.js +1 -0
- package/lib/Types/Bussines.d.ts +25 -0
- package/lib/Types/Call.d.ts +15 -0
- package/lib/Types/Call.js +1 -0
- package/lib/Types/Chat.d.ts +124 -0
- package/lib/Types/Chat.js +7 -0
- package/lib/Types/Contact.d.ts +26 -0
- package/lib/Types/Contact.js +1 -0
- package/lib/Types/Events.d.ts +256 -0
- package/lib/Types/Events.js +1 -0
- package/lib/Types/GroupMetadata.d.ts +71 -0
- package/lib/Types/GroupMetadata.js +1 -0
- package/lib/Types/Label.d.ts +5 -0
- package/lib/Types/Label.js +24 -0
- package/lib/Types/LabelAssociation.d.ts +6 -0
- package/lib/Types/LabelAssociation.js +6 -0
- package/lib/Types/Message.d.ts +62 -0
- package/lib/Types/Message.js +17 -0
- package/lib/Types/Mex.d.ts +2 -0
- package/lib/Types/Mex.js +38 -0
- package/lib/Types/Product.d.ts +79 -0
- package/lib/Types/Product.js +1 -0
- package/lib/Types/RichType.d.ts +2 -0
- package/lib/Types/RichType.js +22 -0
- package/lib/Types/Signal.d.ts +87 -0
- package/lib/Types/Signal.js +1 -0
- package/lib/Types/Socket.d.ts +138 -0
- package/lib/Types/Socket.js +1 -0
- package/lib/Types/State.d.ts +8 -0
- package/lib/Types/State.js +55 -0
- package/lib/Types/USync.d.ts +26 -0
- package/lib/Types/index.d.ts +68 -0
- package/lib/Types/index.js +27 -0
- package/lib/Utils/MessageBuilder.d.ts +2 -0
- package/lib/Utils/MessageBuilder.js +2 -0
- package/lib/Utils/PersistentStore.d.ts +60 -0
- package/lib/Utils/PersistentStore.js +592 -0
- package/lib/Utils/anti-delete.d.ts +74 -0
- package/lib/Utils/anti-delete.js +221 -0
- package/lib/Utils/auth-secure.d.ts +86 -0
- package/lib/Utils/auth-secure.js +764 -0
- package/lib/Utils/auth-utils.d.ts +57 -0
- package/lib/Utils/auth-utils.js +306 -0
- package/lib/Utils/auto-reply.d.ts +47 -0
- package/lib/Utils/auto-reply.js +157 -0
- package/lib/Utils/baileys-event-stream.d.ts +8 -0
- package/lib/Utils/baileys-event-stream.js +62 -0
- package/lib/Utils/browser-utils.d.ts +8 -0
- package/lib/Utils/browser-utils.js +27 -0
- package/lib/Utils/business.d.ts +49 -0
- package/lib/Utils/business.js +239 -0
- package/lib/Utils/button-helper-utils.d.ts +53 -0
- package/lib/Utils/button-helper-utils.js +312 -0
- package/lib/Utils/button-sender.d.ts +54 -0
- package/lib/Utils/button-sender.js +822 -0
- package/lib/Utils/chat-control.d.ts +159 -0
- package/lib/Utils/chat-control.js +230 -0
- package/lib/Utils/chat-history-helpers.d.ts +21 -0
- package/lib/Utils/chat-history-helpers.js +70 -0
- package/lib/Utils/chat-utils.d.ts +407 -0
- package/lib/Utils/chat-utils.js +885 -0
- package/lib/Utils/companion-reg-client-utils.d.ts +4 -0
- package/lib/Utils/companion-reg-client-utils.js +39 -0
- package/lib/Utils/crypto.d.ts +41 -0
- package/lib/Utils/crypto.js +147 -0
- package/lib/Utils/decode-wa-message.d.ts +83 -0
- package/lib/Utils/decode-wa-message.js +316 -0
- package/lib/Utils/event-buffer.d.ts +12 -0
- package/lib/Utils/event-buffer.js +635 -0
- package/lib/Utils/generics.d.ts +69 -0
- package/lib/Utils/generics.js +438 -0
- package/lib/Utils/history-share.d.ts +11 -0
- package/lib/Utils/history-share.js +70 -0
- package/lib/Utils/history.d.ts +90 -0
- package/lib/Utils/history.js +146 -0
- package/lib/Utils/humanizer.d.ts +12 -0
- package/lib/Utils/humanizer.js +73 -0
- package/lib/Utils/identity-change-handler.d.ts +13 -0
- package/lib/Utils/identity-change-handler.js +49 -0
- package/lib/Utils/index.d.ts +57 -0
- package/lib/Utils/index.js +56 -0
- package/lib/Utils/jid-tools.d.ts +6 -0
- package/lib/Utils/jid-tools.js +77 -0
- package/lib/Utils/link-preview.d.ts +12 -0
- package/lib/Utils/link-preview.js +84 -0
- package/lib/Utils/logger.d.ts +4 -0
- package/lib/Utils/logger.js +2 -0
- package/lib/Utils/lt-hash.d.ts +12 -0
- package/lib/Utils/lt-hash.js +26 -0
- package/lib/Utils/make-mutex.d.ts +6 -0
- package/lib/Utils/make-mutex.js +32 -0
- package/lib/Utils/media-messages.d.ts +18 -0
- package/lib/Utils/media-messages.js +70 -0
- package/lib/Utils/media-set.d.ts +13 -0
- package/lib/Utils/media-set.js +171 -0
- package/lib/Utils/message-kind.d.ts +32 -0
- package/lib/Utils/message-kind.js +136 -0
- package/lib/Utils/message-retry-manager.d.ts +79 -0
- package/lib/Utils/message-retry-manager.js +264 -0
- package/lib/Utils/message-search.d.ts +44 -0
- package/lib/Utils/message-search.js +188 -0
- package/lib/Utils/messages-media.d.ts +135 -0
- package/lib/Utils/messages-media.js +868 -0
- package/lib/Utils/messages.d.ts +44 -0
- package/lib/Utils/messages.js +2326 -0
- package/lib/Utils/meta-ai.d.ts +13 -0
- package/lib/Utils/meta-ai.js +74 -0
- package/lib/Utils/mini-app.d.ts +35 -0
- package/lib/Utils/mini-app.js +213 -0
- package/lib/Utils/noise-handler.d.ts +20 -0
- package/lib/Utils/noise-handler.js +200 -0
- package/lib/Utils/offline-node-processor.d.ts +9 -0
- package/lib/Utils/offline-node-processor.js +39 -0
- package/lib/Utils/past-participants.d.ts +14 -0
- package/lib/Utils/past-participants.js +40 -0
- package/lib/Utils/pre-key-manager.d.ts +25 -0
- package/lib/Utils/pre-key-manager.js +105 -0
- package/lib/Utils/process-message.d.ts +82 -0
- package/lib/Utils/process-message.js +808 -0
- package/lib/Utils/qr-render.d.ts +59 -0
- package/lib/Utils/qr-render.js +179 -0
- package/lib/Utils/qrcodegen.d.ts +79 -0
- package/lib/Utils/qrcodegen.js +848 -0
- package/lib/Utils/reporting-utils.d.ts +12 -0
- package/lib/Utils/reporting-utils.js +257 -0
- package/lib/Utils/rich-message-utils.d.ts +48 -0
- package/lib/Utils/rich-message-utils.js +444 -0
- package/lib/Utils/router.d.ts +37 -0
- package/lib/Utils/router.js +165 -0
- package/lib/Utils/scheduled-posts.d.ts +30 -0
- package/lib/Utils/scheduled-posts.js +110 -0
- package/lib/Utils/scheduling.d.ts +42 -0
- package/lib/Utils/scheduling.js +139 -0
- package/lib/Utils/signal.d.ts +82 -0
- package/lib/Utils/signal.js +200 -0
- package/lib/Utils/stanza-ack.d.ts +16 -0
- package/lib/Utils/stanza-ack.js +37 -0
- package/lib/Utils/status.d.ts +50 -0
- package/lib/Utils/status.js +107 -0
- package/lib/Utils/stickerpack.d.ts +51 -0
- package/lib/Utils/stickerpack.js +274 -0
- package/lib/Utils/sync-action-utils.d.ts +2 -0
- package/lib/Utils/sync-action-utils.js +48 -0
- package/lib/Utils/tag.d.ts +12 -0
- package/lib/Utils/tag.js +44 -0
- package/lib/Utils/tc-token-utils.d.ts +29 -0
- package/lib/Utils/tc-token-utils.js +162 -0
- package/lib/Utils/templates.d.ts +76 -0
- package/lib/Utils/templates.js +150 -0
- package/lib/Utils/transcribe.d.ts +12 -0
- package/lib/Utils/transcribe.js +107 -0
- package/lib/Utils/use-cache-manager-auth-state.d.ts +13 -0
- package/lib/Utils/use-cache-manager-auth-state.js +81 -0
- package/lib/Utils/use-multi-file-auth-state.d.ts +10 -0
- package/lib/Utils/use-multi-file-auth-state.js +166 -0
- package/lib/Utils/use-single-file-auth-state.d.ts +10 -0
- package/lib/Utils/use-single-file-auth-state.js +113 -0
- package/lib/Utils/use-sqlite-auth-state.d.ts +11 -0
- package/lib/Utils/use-sqlite-auth-state.js +169 -0
- package/lib/Utils/validate-connection.d.ts +42 -0
- package/lib/Utils/validate-connection.js +198 -0
- package/lib/Utils/vcard.d.ts +58 -0
- package/lib/Utils/vcard.js +104 -0
- package/lib/Utils/voice-note.d.ts +15 -0
- package/lib/Utils/voice-note.js +63 -0
- package/lib/VoIP/audio-feeder.d.ts +18 -0
- package/lib/VoIP/audio-feeder.js +160 -0
- package/lib/VoIP/call-recorder.d.ts +13 -0
- package/lib/VoIP/call-recorder.js +73 -0
- package/lib/VoIP/index.d.ts +86 -0
- package/lib/VoIP/index.js +611 -0
- package/lib/VoIP/relay-transport.d.ts +43 -0
- package/lib/VoIP/relay-transport.js +563 -0
- package/lib/VoIP/signaling.d.ts +26 -0
- package/lib/VoIP/signaling.js +662 -0
- package/lib/VoIP/types.d.ts +69 -0
- package/lib/VoIP/types.js +17 -0
- package/lib/VoIP/wasm-engine.d.ts +120 -0
- package/lib/VoIP/wasm-engine.js +1358 -0
- package/lib/VoIP/worker-bootstrap.d.ts +4 -0
- package/lib/VoIP/worker-bootstrap.js +1046 -0
- package/lib/WABinary/constants.d.ts +61 -0
- package/lib/WABinary/constants.js +1466 -0
- package/lib/WABinary/decode.d.ts +9 -0
- package/lib/WABinary/decode.js +261 -0
- package/lib/WABinary/encode.d.ts +2 -0
- package/lib/WABinary/encode.js +219 -0
- package/lib/WABinary/generic-utils.d.ts +74 -0
- package/lib/WABinary/generic-utils.js +276 -0
- package/lib/WABinary/index.d.ts +5 -0
- package/lib/WABinary/index.js +5 -0
- package/lib/WABinary/jid-utils.d.ts +28 -0
- package/lib/WABinary/jid-utils.js +95 -0
- package/lib/WABinary/types.d.ts +19 -0
- package/lib/WABinary/types.js +1 -0
- package/lib/WAM/BinaryInfo.d.ts +7 -0
- package/lib/WAM/BinaryInfo.js +9 -0
- package/lib/WAM/constants.d.ts +34926 -0
- package/lib/WAM/constants.js +22852 -0
- package/lib/WAM/encode.d.ts +1 -0
- package/lib/WAM/encode.js +149 -0
- package/lib/WAM/index.d.ts +3 -0
- package/lib/WAM/index.js +3 -0
- package/lib/WAUSync/Protocols/USyncContactProtocol.d.ts +36 -0
- package/lib/WAUSync/Protocols/USyncContactProtocol.js +51 -0
- package/lib/WAUSync/Protocols/USyncDeviceProtocol.d.ts +29 -0
- package/lib/WAUSync/Protocols/USyncDeviceProtocol.js +62 -0
- package/lib/WAUSync/Protocols/USyncDisappearingModeProtocol.d.ts +12 -0
- package/lib/WAUSync/Protocols/USyncDisappearingModeProtocol.js +26 -0
- package/lib/WAUSync/Protocols/USyncStatusProtocol.d.ts +12 -0
- package/lib/WAUSync/Protocols/USyncStatusProtocol.js +37 -0
- package/lib/WAUSync/Protocols/USyncUsernameProtocol.d.ts +9 -0
- package/lib/WAUSync/Protocols/USyncUsernameProtocol.js +24 -0
- package/lib/WAUSync/Protocols/UsyncBotProfileProtocol.d.ts +38 -0
- package/lib/WAUSync/Protocols/UsyncBotProfileProtocol.js +50 -0
- package/lib/WAUSync/Protocols/UsyncLIDProtocol.d.ts +14 -0
- package/lib/WAUSync/Protocols/UsyncLIDProtocol.js +28 -0
- package/lib/WAUSync/Protocols/index.d.ts +7 -0
- package/lib/WAUSync/Protocols/index.js +7 -0
- package/lib/WAUSync/USyncQuery.d.ts +20 -0
- package/lib/WAUSync/USyncQuery.js +121 -0
- package/lib/WAUSync/USyncUser.d.ts +16 -0
- package/lib/WAUSync/USyncUser.js +30 -0
- package/lib/WAUSync/index.d.ts +3 -0
- package/lib/WAUSync/index.js +3 -0
- package/lib/assets/wasm/loader.d.ts +5 -0
- package/lib/assets/wasm/loader.js +5 -0
- package/lib/assets/wasm/whatsapp.wasm +0 -0
- package/lib/assets/wasm/worker-modules.d.ts +5 -0
- package/lib/assets/wasm/worker-modules.js +273 -0
- package/lib/index.d.ts +18 -0
- package/lib/index.js +23 -0
- package/package.json +180 -0
- package/postinstall-banner.js +82 -0
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
export function promiseTimeout(ms: any, promise: any): Promise<any>;
|
|
2
|
+
export function bindWaitForEvent(ev: any, event: any): (check: any, timeoutMs: any) => Promise<void>;
|
|
3
|
+
export function trimUndefined(obj: any): any;
|
|
4
|
+
export function bytesToCrockford(buffer: any): string;
|
|
5
|
+
export function encodeNewsletterMessage(message: any): any;
|
|
6
|
+
export namespace BufferJSON {
|
|
7
|
+
function replacer(k: any, value: any): any;
|
|
8
|
+
function reviver(_: any, value: any): any;
|
|
9
|
+
}
|
|
10
|
+
export function getKeyAuthor(key: any, meId?: string): any;
|
|
11
|
+
export function isStringNullOrEmpty(value: any): boolean;
|
|
12
|
+
export function writeRandomPadMax16(msg: any): any;
|
|
13
|
+
export function unpadRandomMax16(e: any): Uint8Array<any>;
|
|
14
|
+
export function generateParticipantHashV2(participants: any): string;
|
|
15
|
+
export function encodeWAMessage(message: any): any;
|
|
16
|
+
export function generateRegistrationId(): number;
|
|
17
|
+
export function encodeBigEndian(e: any, t?: number): Uint8Array<ArrayBuffer>;
|
|
18
|
+
export function toNumber(t: any): any;
|
|
19
|
+
export function unixTimestampSeconds(date?: Date): number;
|
|
20
|
+
export function debouncedTimeout(intervalMs: number | undefined, task: any): {
|
|
21
|
+
start: (newIntervalMs: any, newTask: any) => void;
|
|
22
|
+
cancel: () => void;
|
|
23
|
+
setTask: (newTask: any) => any;
|
|
24
|
+
setInterval: (newInterval: any) => any;
|
|
25
|
+
};
|
|
26
|
+
export function delay(ms: any): Promise<any>;
|
|
27
|
+
export function delayCancellable(ms: any): {
|
|
28
|
+
delay: Promise<any>;
|
|
29
|
+
cancel: () => void;
|
|
30
|
+
};
|
|
31
|
+
export function generateMessageIDV2(userId: any): string;
|
|
32
|
+
export function generateMessageID(): string;
|
|
33
|
+
export function bindWaitForConnectionUpdate(ev: any): (check: any, timeoutMs: any) => Promise<void>;
|
|
34
|
+
export function fetchLatestBaileysVersion(options?: {}): Promise<{
|
|
35
|
+
version: number[];
|
|
36
|
+
isLatest: boolean;
|
|
37
|
+
error?: undefined;
|
|
38
|
+
} | {
|
|
39
|
+
version: number[];
|
|
40
|
+
isLatest: boolean;
|
|
41
|
+
error: unknown;
|
|
42
|
+
}>;
|
|
43
|
+
export function fetchLatestWaWebVersion(options?: {}): Promise<{
|
|
44
|
+
version: number[];
|
|
45
|
+
isLatest: boolean;
|
|
46
|
+
error?: undefined;
|
|
47
|
+
} | {
|
|
48
|
+
version: number[];
|
|
49
|
+
isLatest: boolean;
|
|
50
|
+
error: unknown;
|
|
51
|
+
}>;
|
|
52
|
+
export function fetchBestWaVersion(options?: {}): Promise<{
|
|
53
|
+
version: number[];
|
|
54
|
+
isLatest: boolean;
|
|
55
|
+
source: 'wa-web' | 'baileys-fork' | 'hardcoded-fallback';
|
|
56
|
+
error?: unknown;
|
|
57
|
+
}>;
|
|
58
|
+
export function generateMdTagPrefix(): string;
|
|
59
|
+
export function getStatusFromReceiptType(type: any): any;
|
|
60
|
+
export function getErrorCodeFromStreamError(node: any): {
|
|
61
|
+
reason: any;
|
|
62
|
+
statusCode: number;
|
|
63
|
+
};
|
|
64
|
+
export function getCallStatusFromNode({ tag, attrs }: {
|
|
65
|
+
tag: any;
|
|
66
|
+
attrs: any;
|
|
67
|
+
}): string;
|
|
68
|
+
export function getCodeFromWSError(error: any): number;
|
|
69
|
+
export function isWABusinessPlatform(platform: any): boolean;
|
|
@@ -0,0 +1,438 @@
|
|
|
1
|
+
import { Boom } from '@hapi/boom';
|
|
2
|
+
import { createHash, randomBytes, randomFillSync } from 'crypto';
|
|
3
|
+
import { proto } from '../../WAProto/index.js';
|
|
4
|
+
const baileysVersion = [2, 3000, 1043857760];
|
|
5
|
+
import { DisconnectReason } from '../Types/index.js';
|
|
6
|
+
import { getAllBinaryNodeChildren, jidDecode } from '../WABinary/index.js';
|
|
7
|
+
import { sha256 } from './crypto.js';
|
|
8
|
+
export const BufferJSON = {
|
|
9
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
10
|
+
replacer: (k, value) => {
|
|
11
|
+
if (Buffer.isBuffer(value) || value instanceof Uint8Array || value?.type === 'Buffer') {
|
|
12
|
+
return { type: 'Buffer', data: Buffer.from(value?.data || value).toString('base64') };
|
|
13
|
+
}
|
|
14
|
+
return value;
|
|
15
|
+
},
|
|
16
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
17
|
+
reviver: (_, value) => {
|
|
18
|
+
if (typeof value === 'object' && value !== null && value.type === 'Buffer' && typeof value.data === 'string') {
|
|
19
|
+
return Buffer.from(value.data, 'base64');
|
|
20
|
+
}
|
|
21
|
+
if (typeof value === 'object' && value !== null && !Array.isArray(value)) {
|
|
22
|
+
const keys = Object.keys(value);
|
|
23
|
+
if (keys.length > 0 && keys.every(k => !isNaN(parseInt(k, 10)))) {
|
|
24
|
+
const values = Object.values(value);
|
|
25
|
+
if (values.every(v => typeof v === 'number')) {
|
|
26
|
+
return Buffer.from(values);
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
return value;
|
|
31
|
+
}
|
|
32
|
+
};
|
|
33
|
+
export const getKeyAuthor = (key, meId = 'me') => (key?.fromMe ? meId : key?.participantAlt || key?.remoteJidAlt || key?.participant || key?.remoteJid) || '';
|
|
34
|
+
export const isStringNullOrEmpty = (value) =>
|
|
35
|
+
// eslint-disable-next-line eqeqeq
|
|
36
|
+
value == null || value === '';
|
|
37
|
+
export const writeRandomPadMax16 = (msg) => {
|
|
38
|
+
const pad = randomBytes(1);
|
|
39
|
+
const padLength = (pad[0] & 0x0f) + 1;
|
|
40
|
+
return Buffer.concat([msg, Buffer.alloc(padLength, padLength)]);
|
|
41
|
+
};
|
|
42
|
+
export const unpadRandomMax16 = (e) => {
|
|
43
|
+
const t = new Uint8Array(e);
|
|
44
|
+
if (0 === t.length) {
|
|
45
|
+
throw new Error('unpadPkcs7 given empty bytes');
|
|
46
|
+
}
|
|
47
|
+
var r = t[t.length - 1];
|
|
48
|
+
if (r > t.length) {
|
|
49
|
+
throw new Error(`unpad given ${t.length} bytes, but pad is ${r}`);
|
|
50
|
+
}
|
|
51
|
+
return new Uint8Array(t.buffer, t.byteOffset, t.length - r);
|
|
52
|
+
};
|
|
53
|
+
// code is inspired by whatsmeow
|
|
54
|
+
export const generateParticipantHashV2 = (participants) => {
|
|
55
|
+
participants.sort();
|
|
56
|
+
const sha256Hash = sha256(Buffer.from(participants.join(''))).toString('base64');
|
|
57
|
+
return '2:' + sha256Hash.slice(0, 6);
|
|
58
|
+
};
|
|
59
|
+
export const encodeWAMessage = (message) => writeRandomPadMax16(proto.Message.encode(message).finish());
|
|
60
|
+
export const generateRegistrationId = () => {
|
|
61
|
+
return Uint16Array.from(randomBytes(2))[0] & 16383;
|
|
62
|
+
};
|
|
63
|
+
export const encodeBigEndian = (e, t = 4) => {
|
|
64
|
+
let r = e;
|
|
65
|
+
const a = new Uint8Array(t);
|
|
66
|
+
for (let i = t - 1; i >= 0; i--) {
|
|
67
|
+
a[i] = 255 & r;
|
|
68
|
+
r >>>= 8;
|
|
69
|
+
}
|
|
70
|
+
return a;
|
|
71
|
+
};
|
|
72
|
+
export const toNumber = (t) => typeof t === 'object' && t ? ('toNumber' in t ? t.toNumber() : t.low) : t || 0;
|
|
73
|
+
/** unix timestamp of a date in seconds */
|
|
74
|
+
// JAP@Fix (bug 69): unixTimestampSeconds(date) assumed `date` is always a real Date
|
|
75
|
+
// instance and called date.getTime() unconditionally. Any caller that passed a raw
|
|
76
|
+
// number (Date.now(), or an already-converted unix timestamp) or an ISO string instead
|
|
77
|
+
// of a Date crashed here with "date.getTime is not a function" — this is a coercion
|
|
78
|
+
// bug in THIS function, not a proto/BloksWidget/InteractiveMessage issue (traced and
|
|
79
|
+
// confirmed: normalizeMessageContent/getContentType never touch nested message content,
|
|
80
|
+
// and this function is called before any encode/serialize step even starts). Coerce the
|
|
81
|
+
// common input shapes instead of assuming Date, but keep throwing on genuinely invalid
|
|
82
|
+
// input (NaN) so silent bad-timestamp bugs don't get hidden.
|
|
83
|
+
export const unixTimestampSeconds = (date) => {
|
|
84
|
+
if (date == null) date = new Date(); // null AND undefined both mean "now" (default params only catch undefined)
|
|
85
|
+
const d = date instanceof Date
|
|
86
|
+
? date
|
|
87
|
+
: new Date(typeof date === 'number' && date < 1e12 ? date * 1000 : date); // treat sub-1e12 numbers as already-seconds
|
|
88
|
+
if (Number.isNaN(d.getTime())) {
|
|
89
|
+
throw new TypeError(`unixTimestampSeconds: invalid timestamp input (${typeof date}): ${date}`);
|
|
90
|
+
}
|
|
91
|
+
return d.getTime() / 1000 | 0;
|
|
92
|
+
};
|
|
93
|
+
export const debouncedTimeout = (intervalMs = 1000, task) => {
|
|
94
|
+
let timeout;
|
|
95
|
+
return {
|
|
96
|
+
start: (newIntervalMs, newTask) => {
|
|
97
|
+
task = newTask || task;
|
|
98
|
+
intervalMs = newIntervalMs || intervalMs;
|
|
99
|
+
timeout && clearTimeout(timeout);
|
|
100
|
+
timeout = setTimeout(() => task?.(), intervalMs);
|
|
101
|
+
},
|
|
102
|
+
cancel: () => {
|
|
103
|
+
timeout && clearTimeout(timeout);
|
|
104
|
+
timeout = undefined;
|
|
105
|
+
},
|
|
106
|
+
setTask: (newTask) => (task = newTask),
|
|
107
|
+
setInterval: (newInterval) => (intervalMs = newInterval)
|
|
108
|
+
};
|
|
109
|
+
};
|
|
110
|
+
export const delay = (ms) => delayCancellable(ms).delay;
|
|
111
|
+
export const delayCancellable = (ms) => {
|
|
112
|
+
const stack = new Error().stack;
|
|
113
|
+
let timeout;
|
|
114
|
+
let reject;
|
|
115
|
+
const delay = new Promise((resolve, _reject) => {
|
|
116
|
+
timeout = setTimeout(resolve, ms);
|
|
117
|
+
reject = _reject;
|
|
118
|
+
});
|
|
119
|
+
const cancel = () => {
|
|
120
|
+
clearTimeout(timeout);
|
|
121
|
+
reject(new Boom('Cancelled', {
|
|
122
|
+
statusCode: 500,
|
|
123
|
+
data: {
|
|
124
|
+
stack
|
|
125
|
+
}
|
|
126
|
+
}));
|
|
127
|
+
};
|
|
128
|
+
return { delay, cancel };
|
|
129
|
+
};
|
|
130
|
+
export async function promiseTimeout(ms, promise) {
|
|
131
|
+
if (!ms) {
|
|
132
|
+
return new Promise(promise);
|
|
133
|
+
}
|
|
134
|
+
const stack = new Error().stack;
|
|
135
|
+
// Create a promise that rejects in <ms> milliseconds
|
|
136
|
+
const { delay, cancel } = delayCancellable(ms);
|
|
137
|
+
const p = new Promise((resolve, reject) => {
|
|
138
|
+
delay
|
|
139
|
+
.then(() => reject(new Boom('Timed Out', {
|
|
140
|
+
statusCode: DisconnectReason.timedOut,
|
|
141
|
+
data: {
|
|
142
|
+
stack
|
|
143
|
+
}
|
|
144
|
+
})))
|
|
145
|
+
.catch(err => reject(err));
|
|
146
|
+
promise(resolve, reject);
|
|
147
|
+
}).finally(cancel);
|
|
148
|
+
return p;
|
|
149
|
+
}
|
|
150
|
+
// inspired from whatsmeow code
|
|
151
|
+
// https://github.com/tulir/whatsmeow/blob/64bc969fbe78d31ae0dd443b8d4c80a5d026d07a/send.go#L42
|
|
152
|
+
export const generateMessageIDV2 = (userId) => {
|
|
153
|
+
const data = Buffer.allocUnsafe(44);
|
|
154
|
+
data.writeBigUInt64BE(BigInt(Date.now() / 1000 | 0), 0);
|
|
155
|
+
if (userId) {
|
|
156
|
+
const userStr = userId.split('@')[0].split(':')[0];
|
|
157
|
+
if (userStr) {
|
|
158
|
+
const len = data.write(userStr, 8);
|
|
159
|
+
data.write('@c.us', 8 + len);
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
randomFillSync(data, 28, 16);
|
|
163
|
+
const hash = createHash('sha256').update(data).digest();
|
|
164
|
+
const hex = hash.toString('hex', 0, 9).toUpperCase();
|
|
165
|
+
return '3EB0' + hex;
|
|
166
|
+
};
|
|
167
|
+
// generate a random ID to attach to a message
|
|
168
|
+
export const generateMessageID = () => '3EB0' + randomBytes(18).toString('hex').toUpperCase();
|
|
169
|
+
export function bindWaitForEvent(ev, event) {
|
|
170
|
+
return async (check, timeoutMs) => {
|
|
171
|
+
let listener;
|
|
172
|
+
let closeListener;
|
|
173
|
+
await promiseTimeout(timeoutMs, (resolve, reject) => {
|
|
174
|
+
closeListener = ({ connection, lastDisconnect }) => {
|
|
175
|
+
if (connection === 'close') {
|
|
176
|
+
reject(lastDisconnect?.error || new Boom('Connection Closed', { statusCode: DisconnectReason.connectionClosed }));
|
|
177
|
+
}
|
|
178
|
+
};
|
|
179
|
+
ev.on('connection.update', closeListener);
|
|
180
|
+
listener = async (update) => {
|
|
181
|
+
if (await check(update)) {
|
|
182
|
+
resolve();
|
|
183
|
+
}
|
|
184
|
+
};
|
|
185
|
+
ev.on(event, listener);
|
|
186
|
+
}).finally(() => {
|
|
187
|
+
ev.off(event, listener);
|
|
188
|
+
ev.off('connection.update', closeListener);
|
|
189
|
+
});
|
|
190
|
+
};
|
|
191
|
+
}
|
|
192
|
+
export const bindWaitForConnectionUpdate = (ev) => bindWaitForEvent(ev, 'connection.update');
|
|
193
|
+
/**
|
|
194
|
+
* utility that fetches latest baileys version from the master branch.
|
|
195
|
+
* Use to ensure your WA connection is always on the latest version
|
|
196
|
+
*/
|
|
197
|
+
export const fetchLatestBaileysVersion = async (options = {}) => {
|
|
198
|
+
// Balik ke repo sendiri — J.AP bakal update manual lib/Defaults/index.js
|
|
199
|
+
// di GitHub tiap WA naikin versi minimum.
|
|
200
|
+
const URL = 'https://raw.githubusercontent.com/JAPofc/baileys/main/lib/Defaults/index.js';
|
|
201
|
+
try {
|
|
202
|
+
const response = await fetch(URL, {
|
|
203
|
+
dispatcher: options.dispatcher,
|
|
204
|
+
method: 'GET',
|
|
205
|
+
headers: options.headers
|
|
206
|
+
});
|
|
207
|
+
if (!response.ok) {
|
|
208
|
+
throw new Boom(`Failed to fetch latest Baileys version: ${response.statusText}`, { statusCode: response.status });
|
|
209
|
+
}
|
|
210
|
+
const text = await response.text();
|
|
211
|
+
// JAP@Fix: sebelumnya ambil baris tertentu by index (lines[4]) —
|
|
212
|
+
// rapuh banget, gampang salah baca kalau format file sumbernya
|
|
213
|
+
// berubah dikit (nambah/kurang komentar/baris kosong di atasnya).
|
|
214
|
+
// Sekarang cari pattern `const version = [...]` di SELURUH isi
|
|
215
|
+
// file, gak peduli ada di baris keberapa.
|
|
216
|
+
const versionMatch = text.match(/const version\s*=\s*\[(\d+),\s*(\d+),\s*(\d+)\]/);
|
|
217
|
+
if (versionMatch) {
|
|
218
|
+
const version = [parseInt(versionMatch[1]), parseInt(versionMatch[2]), parseInt(versionMatch[3])];
|
|
219
|
+
return {
|
|
220
|
+
version,
|
|
221
|
+
isLatest: true
|
|
222
|
+
};
|
|
223
|
+
}
|
|
224
|
+
else {
|
|
225
|
+
throw new Error('Could not parse version from Defaults/index.ts');
|
|
226
|
+
}
|
|
227
|
+
}
|
|
228
|
+
catch (error) {
|
|
229
|
+
return {
|
|
230
|
+
version: baileysVersion,
|
|
231
|
+
isLatest: false,
|
|
232
|
+
error
|
|
233
|
+
};
|
|
234
|
+
}
|
|
235
|
+
};
|
|
236
|
+
/**
|
|
237
|
+
* A utility that fetches the latest web version of whatsapp.
|
|
238
|
+
* Use to ensure your WA connection is always on the latest version
|
|
239
|
+
*/
|
|
240
|
+
export const fetchLatestWaWebVersion = async (options = {}) => {
|
|
241
|
+
try {
|
|
242
|
+
// Absolute minimal headers required to bypass anti-bot detection
|
|
243
|
+
const defaultHeaders = {
|
|
244
|
+
'sec-fetch-site': 'none',
|
|
245
|
+
'user-agent': 'Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/131.0.0.0 Safari/537.36'
|
|
246
|
+
};
|
|
247
|
+
const headers = { ...defaultHeaders, ...options.headers };
|
|
248
|
+
const response = await fetch('https://web.whatsapp.com/sw.js', {
|
|
249
|
+
...options,
|
|
250
|
+
method: 'GET',
|
|
251
|
+
headers
|
|
252
|
+
});
|
|
253
|
+
if (!response.ok) {
|
|
254
|
+
throw new Boom(`Failed to fetch sw.js: ${response.statusText}`, { statusCode: response.status });
|
|
255
|
+
}
|
|
256
|
+
const data = await response.text();
|
|
257
|
+
const regex = /\\?"client_revision\\?":\s*(\d+)/;
|
|
258
|
+
const match = data.match(regex);
|
|
259
|
+
if (!match?.[1]) {
|
|
260
|
+
return {
|
|
261
|
+
version: baileysVersion,
|
|
262
|
+
isLatest: false,
|
|
263
|
+
error: {
|
|
264
|
+
message: 'Could not find client revision in the fetched content'
|
|
265
|
+
}
|
|
266
|
+
};
|
|
267
|
+
}
|
|
268
|
+
const clientRevision = match[1];
|
|
269
|
+
return {
|
|
270
|
+
version: [2, 3000, +clientRevision],
|
|
271
|
+
isLatest: true
|
|
272
|
+
};
|
|
273
|
+
}
|
|
274
|
+
catch (error) {
|
|
275
|
+
return {
|
|
276
|
+
version: baileysVersion,
|
|
277
|
+
isLatest: false,
|
|
278
|
+
error
|
|
279
|
+
};
|
|
280
|
+
}
|
|
281
|
+
};
|
|
282
|
+
/**
|
|
283
|
+
* JAP@Fix (bug 64): the comment on `version` in Defaults/index.js has long
|
|
284
|
+
* recommended calling `fetchLatestWaWebVersion()` first (parses WA's own
|
|
285
|
+
* sw.js — most accurate, and sidesteps the upstream `isLatest:true`-while-stale
|
|
286
|
+
* bug, upstream#2679), falling back to `fetchLatestBaileysVersion()`,
|
|
287
|
+
* and only then the hardcoded constant — but nothing actually implemented
|
|
288
|
+
* that chain, so it was on every consumer to hand-roll it (or, more likely,
|
|
289
|
+
* skip it, which is how a bot ends up pinned to a stale `version` and starts
|
|
290
|
+
* getting rejected with 405 during pairing once WA bumps its minimum — see
|
|
291
|
+
* upstream#2370 / #2485). This runs the documented chain for real.
|
|
292
|
+
* Never throws: worst case it resolves to the hardcoded fallback with
|
|
293
|
+
* isLatest:false, same as calling either function alone would.
|
|
294
|
+
*/
|
|
295
|
+
export const fetchBestWaVersion = async (options = {}) => {
|
|
296
|
+
const webResult = await fetchLatestWaWebVersion(options);
|
|
297
|
+
if (webResult.isLatest) {
|
|
298
|
+
return { ...webResult, source: 'wa-web' };
|
|
299
|
+
}
|
|
300
|
+
const baileysResult = await fetchLatestBaileysVersion(options);
|
|
301
|
+
if (baileysResult.isLatest) {
|
|
302
|
+
return { ...baileysResult, source: 'baileys-fork' };
|
|
303
|
+
}
|
|
304
|
+
return { ...baileysResult, source: 'hardcoded-fallback' };
|
|
305
|
+
};
|
|
306
|
+
/** unique message tag prefix for MD clients */
|
|
307
|
+
export const generateMdTagPrefix = () => {
|
|
308
|
+
const bytes = randomBytes(4);
|
|
309
|
+
return `${bytes.readUInt16BE()}.${bytes.readUInt16BE(2)}-`;
|
|
310
|
+
};
|
|
311
|
+
const STATUS_MAP = {
|
|
312
|
+
sender: proto.WebMessageInfo.Status.SERVER_ACK,
|
|
313
|
+
played: proto.WebMessageInfo.Status.PLAYED,
|
|
314
|
+
read: proto.WebMessageInfo.Status.READ,
|
|
315
|
+
'read-self': proto.WebMessageInfo.Status.READ
|
|
316
|
+
};
|
|
317
|
+
/**
|
|
318
|
+
* Given a type of receipt, returns what the new status of the message should be
|
|
319
|
+
* @param type type from receipt
|
|
320
|
+
*/
|
|
321
|
+
export const getStatusFromReceiptType = (type) => {
|
|
322
|
+
const status = STATUS_MAP[type];
|
|
323
|
+
if (typeof type === 'undefined') {
|
|
324
|
+
return proto.WebMessageInfo.Status.DELIVERY_ACK;
|
|
325
|
+
}
|
|
326
|
+
return status;
|
|
327
|
+
};
|
|
328
|
+
const CODE_MAP = {
|
|
329
|
+
conflict: DisconnectReason.connectionReplaced
|
|
330
|
+
};
|
|
331
|
+
/**
|
|
332
|
+
* Stream errors generally provide a reason, map that to a baileys DisconnectReason
|
|
333
|
+
* @param reason the string reason given, eg. "conflict"
|
|
334
|
+
*/
|
|
335
|
+
export const getErrorCodeFromStreamError = (node) => {
|
|
336
|
+
const [reasonNode] = getAllBinaryNodeChildren(node);
|
|
337
|
+
let reason = reasonNode?.tag || 'unknown';
|
|
338
|
+
const statusCode = +(node.attrs.code || CODE_MAP[reason] || DisconnectReason.badSession);
|
|
339
|
+
if (statusCode === DisconnectReason.restartRequired) {
|
|
340
|
+
reason = 'restart required';
|
|
341
|
+
}
|
|
342
|
+
return {
|
|
343
|
+
reason,
|
|
344
|
+
statusCode
|
|
345
|
+
};
|
|
346
|
+
};
|
|
347
|
+
export const getCallStatusFromNode = ({ tag, attrs }) => {
|
|
348
|
+
let status;
|
|
349
|
+
switch (tag) {
|
|
350
|
+
case 'offer':
|
|
351
|
+
case 'offer_notice':
|
|
352
|
+
status = 'offer';
|
|
353
|
+
break;
|
|
354
|
+
case 'terminate':
|
|
355
|
+
if (attrs.reason === 'timeout') {
|
|
356
|
+
status = 'timeout';
|
|
357
|
+
}
|
|
358
|
+
else {
|
|
359
|
+
//fired when accepted/rejected/timeout/caller hangs up
|
|
360
|
+
status = 'terminate';
|
|
361
|
+
}
|
|
362
|
+
break;
|
|
363
|
+
case 'preaccept':
|
|
364
|
+
status = 'preaccept';
|
|
365
|
+
break;
|
|
366
|
+
case 'transport':
|
|
367
|
+
status = 'transport';
|
|
368
|
+
break;
|
|
369
|
+
case 'relaylatency':
|
|
370
|
+
status = 'relaylatency';
|
|
371
|
+
break;
|
|
372
|
+
case 'reject':
|
|
373
|
+
status = 'reject';
|
|
374
|
+
break;
|
|
375
|
+
case 'accept':
|
|
376
|
+
status = 'accept';
|
|
377
|
+
break;
|
|
378
|
+
default:
|
|
379
|
+
status = 'ringing';
|
|
380
|
+
break;
|
|
381
|
+
}
|
|
382
|
+
return status;
|
|
383
|
+
};
|
|
384
|
+
const UNEXPECTED_SERVER_CODE_TEXT = 'Unexpected server response: ';
|
|
385
|
+
export const getCodeFromWSError = (error) => {
|
|
386
|
+
let statusCode = 500;
|
|
387
|
+
if (error?.message?.includes(UNEXPECTED_SERVER_CODE_TEXT)) {
|
|
388
|
+
const code = +error?.message.slice(UNEXPECTED_SERVER_CODE_TEXT.length);
|
|
389
|
+
if (!Number.isNaN(code) && code >= 400) {
|
|
390
|
+
statusCode = code;
|
|
391
|
+
}
|
|
392
|
+
}
|
|
393
|
+
else if (
|
|
394
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
395
|
+
error?.code?.startsWith('E') ||
|
|
396
|
+
error?.message?.includes('timed out')) {
|
|
397
|
+
// handle ETIMEOUT, ENOTFOUND etc
|
|
398
|
+
statusCode = 408;
|
|
399
|
+
}
|
|
400
|
+
return statusCode;
|
|
401
|
+
};
|
|
402
|
+
/**
|
|
403
|
+
* Is the given platform WA business
|
|
404
|
+
* @param platform AuthenticationCreds.platform
|
|
405
|
+
*/
|
|
406
|
+
export const isWABusinessPlatform = (platform) => {
|
|
407
|
+
return platform === 'smbi' || platform === 'smba';
|
|
408
|
+
};
|
|
409
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
410
|
+
export function trimUndefined(obj) {
|
|
411
|
+
for (const key in obj) {
|
|
412
|
+
if (typeof obj[key] === 'undefined') {
|
|
413
|
+
delete obj[key];
|
|
414
|
+
}
|
|
415
|
+
}
|
|
416
|
+
return obj;
|
|
417
|
+
}
|
|
418
|
+
const CROCKFORD_CHARACTERS = '123456789ABCDEFGHJKLMNPQRSTVWXYZ';
|
|
419
|
+
export function bytesToCrockford(buffer) {
|
|
420
|
+
let value = 0;
|
|
421
|
+
let bitCount = 0;
|
|
422
|
+
const crockford = [];
|
|
423
|
+
for (const element of buffer) {
|
|
424
|
+
value = (value << 8) | (element & 0xff);
|
|
425
|
+
bitCount += 8;
|
|
426
|
+
while (bitCount >= 5) {
|
|
427
|
+
crockford.push(CROCKFORD_CHARACTERS.charAt((value >>> (bitCount - 5)) & 31));
|
|
428
|
+
bitCount -= 5;
|
|
429
|
+
}
|
|
430
|
+
}
|
|
431
|
+
if (bitCount > 0) {
|
|
432
|
+
crockford.push(CROCKFORD_CHARACTERS.charAt((value << (5 - bitCount)) & 31));
|
|
433
|
+
}
|
|
434
|
+
return crockford.join('');
|
|
435
|
+
}
|
|
436
|
+
export function encodeNewsletterMessage(message) {
|
|
437
|
+
return proto.Message.encode(message).finish();
|
|
438
|
+
}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
export declare const getGroupHistoryFromStore: (store: any, groupJid: string, limit?: number) => any[];
|
|
2
|
+
export interface ShareGroupHistoryOptions {
|
|
3
|
+
groupJid: string;
|
|
4
|
+
members: string | string[];
|
|
5
|
+
messages: any[];
|
|
6
|
+
limit?: number;
|
|
7
|
+
greeting?: string | boolean;
|
|
8
|
+
delayMs?: number;
|
|
9
|
+
forceForward?: boolean;
|
|
10
|
+
}
|
|
11
|
+
export declare const shareGroupHistory: (sock: any, opts: ShareGroupHistoryOptions) => Promise<{ groupJid: string; members: string[]; perMember: number; sent: number; failed: { member: string; error: string }[] }>;
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* JAP@Add --- client-side group "history sharing" for new members.
|
|
3
|
+
*
|
|
4
|
+
* WhatsApp's native history-sharing wire format hasn't been captured by any
|
|
5
|
+
* public library, so this helper implements the same *outcome* with public
|
|
6
|
+
* primitives: it forwards the group's recent messages into each new member's
|
|
7
|
+
* DM (optionally with a greeting), with a polite delay between forwards.
|
|
8
|
+
*
|
|
9
|
+
* ```js
|
|
10
|
+
* import { shareGroupHistory, getGroupHistoryFromStore } from '@japofc/baileys'
|
|
11
|
+
* const messages = getGroupHistoryFromStore(store, groupJid, 10)
|
|
12
|
+
* await shareGroupHistory(sock, { groupJid, members: ['62812@s.whatsapp.net'], messages })
|
|
13
|
+
* ```
|
|
14
|
+
*/
|
|
15
|
+
import { Boom } from '@hapi/boom';
|
|
16
|
+
import { copyNForward } from './chat-history-helpers.js';
|
|
17
|
+
import { delay } from './generics.js';
|
|
18
|
+
|
|
19
|
+
/** Pull the last-N cached messages for a group out of an in-memory store. */
|
|
20
|
+
export const getGroupHistoryFromStore = (store, groupJid, limit = 10) => {
|
|
21
|
+
if (!groupJid) {
|
|
22
|
+
throw new Boom('getGroupHistoryFromStore(store, groupJid) needs a group JID', { statusCode: 400 });
|
|
23
|
+
}
|
|
24
|
+
const bucket = store?.messages?.[groupJid];
|
|
25
|
+
const arr = Array.isArray(bucket) ? bucket : bucket?.array || [];
|
|
26
|
+
if (!arr.length) {
|
|
27
|
+
throw new Boom(`no cached messages for ${groupJid} (store empty or not bound?)`, { statusCode: 404 });
|
|
28
|
+
}
|
|
29
|
+
return arr.slice(-Math.max(1, limit));
|
|
30
|
+
};
|
|
31
|
+
|
|
32
|
+
/**
|
|
33
|
+
* Forward recent group history to new members' DMs.
|
|
34
|
+
* Returns `{ groupJid, members, perMember, sent, failed }`.
|
|
35
|
+
*/
|
|
36
|
+
export const shareGroupHistory = async (sock, { groupJid, members, messages = [], limit = 10, greeting, delayMs = 1200, forceForward = false } = {}) => {
|
|
37
|
+
if (!sock || typeof sock.sendMessage !== 'function') {
|
|
38
|
+
throw new Boom('shareGroupHistory(sock, ...) requires an active socket', { statusCode: 400 });
|
|
39
|
+
}
|
|
40
|
+
if (!groupJid || typeof groupJid !== 'string') {
|
|
41
|
+
throw new Boom('shareGroupHistory needs { groupJid }', { statusCode: 400 });
|
|
42
|
+
}
|
|
43
|
+
const targets = Array.isArray(members) ? members : [members];
|
|
44
|
+
if (!targets.length || targets.some((m) => typeof m !== 'string' || !m)) {
|
|
45
|
+
throw new Boom('shareGroupHistory needs { members } (JID string or array)', { statusCode: 400 });
|
|
46
|
+
}
|
|
47
|
+
if (!Array.isArray(messages) || !messages.length) {
|
|
48
|
+
throw new Boom('shareGroupHistory needs { messages } (recent group WebMessages)', { statusCode: 400 });
|
|
49
|
+
}
|
|
50
|
+
const slice = messages.slice(-Math.max(1, limit));
|
|
51
|
+
const out = { groupJid, members: targets, perMember: slice.length, sent: 0, failed: [] };
|
|
52
|
+
for (const member of targets) {
|
|
53
|
+
try {
|
|
54
|
+
if (greeting) {
|
|
55
|
+
await sock.sendMessage(member, { text: typeof greeting === 'string' ? greeting : `Recent history from ${groupJid} 👇` });
|
|
56
|
+
}
|
|
57
|
+
for (const msg of slice) {
|
|
58
|
+
await copyNForward(sock, member, msg, forceForward);
|
|
59
|
+
if (delayMs > 0) {
|
|
60
|
+
await delay(delayMs);
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
out.sent += 1;
|
|
64
|
+
}
|
|
65
|
+
catch (err) {
|
|
66
|
+
out.failed.push({ member, error: err?.message || String(err) });
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
return out;
|
|
70
|
+
};
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
export function downloadHistory(msg: any, options: any): Promise<any>;
|
|
2
|
+
export function processHistoryMessage(item: any, logger: any): {
|
|
3
|
+
messages: any[];
|
|
4
|
+
contacts: any[];
|
|
5
|
+
chats: any[];
|
|
6
|
+
lidPnMappings: any[];
|
|
7
|
+
pastParticipants?: undefined;
|
|
8
|
+
syncType?: undefined;
|
|
9
|
+
progress?: undefined;
|
|
10
|
+
} | {
|
|
11
|
+
chats: any[];
|
|
12
|
+
contacts: ({
|
|
13
|
+
id: any;
|
|
14
|
+
name: any;
|
|
15
|
+
username: any;
|
|
16
|
+
lid: any;
|
|
17
|
+
phoneNumber: any;
|
|
18
|
+
verifiedName?: undefined;
|
|
19
|
+
notify?: undefined;
|
|
20
|
+
} | {
|
|
21
|
+
id: any;
|
|
22
|
+
verifiedName: any;
|
|
23
|
+
name?: undefined;
|
|
24
|
+
username?: undefined;
|
|
25
|
+
lid?: undefined;
|
|
26
|
+
phoneNumber?: undefined;
|
|
27
|
+
notify?: undefined;
|
|
28
|
+
} | {
|
|
29
|
+
id: any;
|
|
30
|
+
notify: any;
|
|
31
|
+
name?: undefined;
|
|
32
|
+
username?: undefined;
|
|
33
|
+
lid?: undefined;
|
|
34
|
+
phoneNumber?: undefined;
|
|
35
|
+
verifiedName?: undefined;
|
|
36
|
+
})[];
|
|
37
|
+
messages: any[];
|
|
38
|
+
lidPnMappings: {
|
|
39
|
+
lid: any;
|
|
40
|
+
pn: any;
|
|
41
|
+
}[];
|
|
42
|
+
pastParticipants: any;
|
|
43
|
+
syncType: any;
|
|
44
|
+
progress: any;
|
|
45
|
+
};
|
|
46
|
+
export function downloadAndProcessHistorySyncNotification(msg: any, options: any, logger: any): Promise<{
|
|
47
|
+
messages: any[];
|
|
48
|
+
contacts: any[];
|
|
49
|
+
chats: any[];
|
|
50
|
+
lidPnMappings: any[];
|
|
51
|
+
pastParticipants?: undefined;
|
|
52
|
+
syncType?: undefined;
|
|
53
|
+
progress?: undefined;
|
|
54
|
+
} | {
|
|
55
|
+
chats: any[];
|
|
56
|
+
contacts: ({
|
|
57
|
+
id: any;
|
|
58
|
+
name: any;
|
|
59
|
+
username: any;
|
|
60
|
+
lid: any;
|
|
61
|
+
phoneNumber: any;
|
|
62
|
+
verifiedName?: undefined;
|
|
63
|
+
notify?: undefined;
|
|
64
|
+
} | {
|
|
65
|
+
id: any;
|
|
66
|
+
verifiedName: any;
|
|
67
|
+
name?: undefined;
|
|
68
|
+
username?: undefined;
|
|
69
|
+
lid?: undefined;
|
|
70
|
+
phoneNumber?: undefined;
|
|
71
|
+
notify?: undefined;
|
|
72
|
+
} | {
|
|
73
|
+
id: any;
|
|
74
|
+
notify: any;
|
|
75
|
+
name?: undefined;
|
|
76
|
+
username?: undefined;
|
|
77
|
+
lid?: undefined;
|
|
78
|
+
phoneNumber?: undefined;
|
|
79
|
+
verifiedName?: undefined;
|
|
80
|
+
})[];
|
|
81
|
+
messages: any[];
|
|
82
|
+
lidPnMappings: {
|
|
83
|
+
lid: any;
|
|
84
|
+
pn: any;
|
|
85
|
+
}[];
|
|
86
|
+
pastParticipants: any;
|
|
87
|
+
syncType: any;
|
|
88
|
+
progress: any;
|
|
89
|
+
}>;
|
|
90
|
+
export function getHistoryMsg(message: any): any;
|