@hbmodsofc/baileys 1.0.6
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/LICENSE +21 -0
- package/README.MD +1276 -0
- package/WAProto/index.js +169661 -0
- package/engine-requirements.js +10 -0
- package/lib/Defaults/baileys-version.json +3 -0
- package/lib/Defaults/index.d.ts +53 -0
- package/lib/Defaults/index.js +147 -0
- package/lib/Defaults/phonenumber-mcc.json +223 -0
- package/lib/Signal/Group/ciphertext-message.d.ts +9 -0
- package/lib/Signal/Group/ciphertext-message.js +15 -0
- package/lib/Signal/Group/group-session-builder.d.ts +14 -0
- package/lib/Signal/Group/group-session-builder.js +64 -0
- package/lib/Signal/Group/group_cipher.d.ts +17 -0
- package/lib/Signal/Group/group_cipher.js +96 -0
- package/lib/Signal/Group/index.d.ts +11 -0
- package/lib/Signal/Group/index.js +57 -0
- package/lib/Signal/Group/keyhelper.d.ts +10 -0
- package/lib/Signal/Group/keyhelper.js +55 -0
- package/lib/Signal/Group/queue-job.d.ts +1 -0
- package/lib/Signal/Group/queue-job.js +57 -0
- package/lib/Signal/Group/sender-chain-key.d.ts +13 -0
- package/lib/Signal/Group/sender-chain-key.js +34 -0
- package/lib/Signal/Group/sender-key-distribution-message.d.ts +16 -0
- package/lib/Signal/Group/sender-key-distribution-message.js +66 -0
- package/lib/Signal/Group/sender-key-message.d.ts +18 -0
- package/lib/Signal/Group/sender-key-message.js +69 -0
- package/lib/Signal/Group/sender-key-name.d.ts +17 -0
- package/lib/Signal/Group/sender-key-name.js +51 -0
- package/lib/Signal/Group/sender-key-record.d.ts +30 -0
- package/lib/Signal/Group/sender-key-record.js +53 -0
- package/lib/Signal/Group/sender-key-state.d.ts +38 -0
- package/lib/Signal/Group/sender-key-state.js +99 -0
- package/lib/Signal/Group/sender-message-key.d.ts +11 -0
- package/lib/Signal/Group/sender-message-key.js +29 -0
- package/lib/Signal/libsignal.d.ts +3 -0
- package/lib/Signal/libsignal.js +174 -0
- package/lib/Socket/Client/abstract-socket-client.d.ts +17 -0
- package/lib/Socket/Client/abstract-socket-client.js +13 -0
- package/lib/Socket/Client/index.d.ts +3 -0
- package/lib/Socket/Client/index.js +19 -0
- package/lib/Socket/Client/mobile-socket-client.d.ts +13 -0
- package/lib/Socket/Client/mobile-socket-client.js +65 -0
- package/lib/Socket/Client/web-socket-client.d.ts +12 -0
- package/lib/Socket/Client/web-socket-client.js +62 -0
- package/lib/Socket/business.d.ts +171 -0
- package/lib/Socket/business.js +260 -0
- package/lib/Socket/chats.d.ts +267 -0
- package/lib/Socket/chats.js +915 -0
- package/lib/Socket/groups.d.ts +115 -0
- package/lib/Socket/groups.js +317 -0
- package/lib/Socket/hbmods.d.ts +253 -0
- package/lib/Socket/hbmods.js +1 -0
- package/lib/Socket/index.d.ts +173 -0
- package/lib/Socket/index.js +11 -0
- package/lib/Socket/messages-recv.d.ts +161 -0
- package/lib/Socket/messages-recv.js +1110 -0
- package/lib/Socket/messages-send.d.ts +149 -0
- package/lib/Socket/messages-send.js +909 -0
- package/lib/Socket/newsletter.d.ts +134 -0
- package/lib/Socket/newsletter.js +250 -0
- package/lib/Socket/registration.d.ts +267 -0
- package/lib/Socket/registration.js +166 -0
- package/lib/Socket/socket.d.ts +43 -0
- package/lib/Socket/socket.js +654 -0
- package/lib/Socket/usync.d.ts +36 -0
- package/lib/Socket/usync.js +70 -0
- package/lib/Store/index.d.ts +3 -0
- package/lib/Store/index.js +10 -0
- package/lib/Store/make-cache-manager-store.d.ts +13 -0
- package/lib/Store/make-cache-manager-store.js +83 -0
- package/lib/Store/make-in-memory-store.d.ts +118 -0
- package/lib/Store/make-in-memory-store.js +427 -0
- package/lib/Store/make-ordered-dictionary.d.ts +13 -0
- package/lib/Store/make-ordered-dictionary.js +81 -0
- package/lib/Store/object-repository.d.ts +10 -0
- package/lib/Store/object-repository.js +27 -0
- package/lib/Types/Auth.d.ts +110 -0
- package/lib/Types/Auth.js +2 -0
- package/lib/Types/Call.d.ts +13 -0
- package/lib/Types/Call.js +2 -0
- package/lib/Types/Chat.d.ts +102 -0
- package/lib/Types/Chat.js +4 -0
- package/lib/Types/Contact.d.ts +19 -0
- package/lib/Types/Contact.js +2 -0
- package/lib/Types/Events.d.ts +157 -0
- package/lib/Types/Events.js +2 -0
- package/lib/Types/GroupMetadata.d.ts +55 -0
- package/lib/Types/GroupMetadata.js +2 -0
- package/lib/Types/Label.d.ts +35 -0
- package/lib/Types/Label.js +27 -0
- package/lib/Types/LabelAssociation.d.ts +29 -0
- package/lib/Types/LabelAssociation.js +9 -0
- package/lib/Types/Message.d.ts +273 -0
- package/lib/Types/Message.js +9 -0
- package/lib/Types/Newsletter.d.ts +103 -0
- package/lib/Types/Newsletter.js +38 -0
- package/lib/Types/Product.d.ts +78 -0
- package/lib/Types/Product.js +2 -0
- package/lib/Types/Signal.d.ts +57 -0
- package/lib/Types/Signal.js +2 -0
- package/lib/Types/Socket.d.ts +111 -0
- package/lib/Types/Socket.js +2 -0
- package/lib/Types/State.d.ts +27 -0
- package/lib/Types/State.js +2 -0
- package/lib/Types/USync.d.ts +25 -0
- package/lib/Types/USync.js +2 -0
- package/lib/Types/index.d.ts +57 -0
- package/lib/Types/index.js +42 -0
- package/lib/Utils/auth-utils.d.ts +18 -0
- package/lib/Utils/auth-utils.js +206 -0
- package/lib/Utils/baileys-event-stream.d.ts +16 -0
- package/lib/Utils/baileys-event-stream.js +63 -0
- package/lib/Utils/business.d.ts +22 -0
- package/lib/Utils/business.js +234 -0
- package/lib/Utils/chat-utils.d.ts +71 -0
- package/lib/Utils/chat-utils.js +729 -0
- package/lib/Utils/crypto.d.ts +41 -0
- package/lib/Utils/crypto.js +151 -0
- package/lib/Utils/decode-wa-message.d.ts +19 -0
- package/lib/Utils/decode-wa-message.js +198 -0
- package/lib/Utils/event-buffer.d.ts +35 -0
- package/lib/Utils/event-buffer.js +514 -0
- package/lib/Utils/generics.d.ts +92 -0
- package/lib/Utils/generics.js +423 -0
- package/lib/Utils/history.d.ts +15 -0
- package/lib/Utils/history.js +96 -0
- package/lib/Utils/index.d.ts +17 -0
- package/lib/Utils/index.js +33 -0
- package/lib/Utils/link-preview.d.ts +21 -0
- package/lib/Utils/link-preview.js +93 -0
- package/lib/Utils/logger.d.ts +4 -0
- package/lib/Utils/logger.js +7 -0
- package/lib/Utils/lt-hash.d.ts +12 -0
- package/lib/Utils/lt-hash.js +51 -0
- package/lib/Utils/make-mutex.d.ts +7 -0
- package/lib/Utils/make-mutex.js +43 -0
- package/lib/Utils/messages-media.d.ts +116 -0
- package/lib/Utils/messages-media.js +819 -0
- package/lib/Utils/messages.d.ts +77 -0
- package/lib/Utils/messages.js +816 -0
- package/lib/Utils/noise-handler.d.ts +21 -0
- package/lib/Utils/noise-handler.js +155 -0
- package/lib/Utils/process-message.d.ts +41 -0
- package/lib/Utils/process-message.js +321 -0
- package/lib/Utils/signal.d.ts +32 -0
- package/lib/Utils/signal.js +153 -0
- package/lib/Utils/use-multi-file-auth-state.d.ts +13 -0
- package/lib/Utils/use-multi-file-auth-state.js +119 -0
- package/lib/Utils/validate-connection.d.ts +11 -0
- package/lib/Utils/validate-connection.js +229 -0
- package/lib/WABinary/constants.d.ts +30 -0
- package/lib/WABinary/constants.js +40 -0
- package/lib/WABinary/decode.d.ts +7 -0
- package/lib/WABinary/decode.js +252 -0
- package/lib/WABinary/encode.d.ts +3 -0
- package/lib/WABinary/encode.js +265 -0
- package/lib/WABinary/generic-utils.d.ts +17 -0
- package/lib/WABinary/generic-utils.js +198 -0
- package/lib/WABinary/index.d.ts +5 -0
- package/lib/WABinary/index.js +21 -0
- package/lib/WABinary/jid-utils.d.ts +31 -0
- package/lib/WABinary/jid-utils.js +62 -0
- package/lib/WABinary/types.d.ts +18 -0
- package/lib/WABinary/types.js +2 -0
- package/lib/WAM/BinaryInfo.d.ts +17 -0
- package/lib/WAM/BinaryInfo.js +13 -0
- package/lib/WAM/constants.d.ts +38 -0
- package/lib/WAM/constants.js +15350 -0
- package/lib/WAM/encode.d.ts +3 -0
- package/lib/WAM/encode.js +155 -0
- package/lib/WAM/index.d.ts +3 -0
- package/lib/WAM/index.js +19 -0
- package/lib/WAUSync/Protocols/USyncContactProtocol.d.ts +9 -0
- package/lib/WAUSync/Protocols/USyncContactProtocol.js +32 -0
- package/lib/WAUSync/Protocols/USyncDeviceProtocol.d.ts +22 -0
- package/lib/WAUSync/Protocols/USyncDeviceProtocol.js +57 -0
- package/lib/WAUSync/Protocols/USyncDisappearingModeProtocol.d.ts +12 -0
- package/lib/WAUSync/Protocols/USyncDisappearingModeProtocol.js +30 -0
- package/lib/WAUSync/Protocols/USyncStatusProtocol.d.ts +12 -0
- package/lib/WAUSync/Protocols/USyncStatusProtocol.js +42 -0
- package/lib/WAUSync/Protocols/UsyncBotProfileProtocol.d.ts +25 -0
- package/lib/WAUSync/Protocols/UsyncBotProfileProtocol.js +53 -0
- package/lib/WAUSync/Protocols/UsyncLIDProtocol.d.ts +8 -0
- package/lib/WAUSync/Protocols/UsyncLIDProtocol.js +24 -0
- package/lib/WAUSync/Protocols/index.d.ts +4 -0
- package/lib/WAUSync/Protocols/index.js +20 -0
- package/lib/WAUSync/USyncQuery.d.ts +28 -0
- package/lib/WAUSync/USyncQuery.js +89 -0
- package/lib/WAUSync/USyncUser.d.ts +12 -0
- package/lib/WAUSync/USyncUser.js +26 -0
- package/lib/WAUSync/index.d.ts +3 -0
- package/lib/WAUSync/index.js +19 -0
- package/lib/index.d.ts +12 -0
- package/lib/index.js +58 -0
- package/package.json +106 -0
package/README.MD
ADDED
|
@@ -0,0 +1,1276 @@
|
|
|
1
|
+
# <div align='center'>@hbmodsofc/baileys</div>
|
|
2
|
+
|
|
3
|
+
<div align='center'>
|
|
4
|
+
|
|
5
|
+
[](https://www.npmjs.com/package/@hbmodsofc/baileys)
|
|
6
|
+
[](LICENSE)
|
|
7
|
+
[](https://www.npmjs.com/package/@hbmodsofc/baileys)
|
|
8
|
+
|
|
9
|
+
</div>
|
|
10
|
+
|
|
11
|
+
## ⚠️ Warning
|
|
12
|
+
|
|
13
|
+
This project is not affiliated, associated, authorized, endorsed, or officially connected with WhatsApp or its subsidiaries. WhatsApp's official website is at whatsapp.com.
|
|
14
|
+
|
|
15
|
+
@hbmodsofc/baileys administrators do not support the use of this application to violate WhatsApp's Terms of Service. We emphasize the user's personal responsibility to use it fairly and responsibly.
|
|
16
|
+
|
|
17
|
+
Use it wisely. Avoid spam. Don't overuse automation.
|
|
18
|
+
|
|
19
|
+
## 📦 Installation
|
|
20
|
+
|
|
21
|
+
### Stable Version (Recommended)
|
|
22
|
+
|
|
23
|
+
```bash
|
|
24
|
+
npm i @hbmodsofc/baileys
|
|
25
|
+
```
|
|
26
|
+
|
|
27
|
+
### Edge Version (Latest Features)
|
|
28
|
+
|
|
29
|
+
```bash
|
|
30
|
+
npm i @hbmodsofc/baileys@latest
|
|
31
|
+
# or
|
|
32
|
+
yarn add @hbmodsofc/baileys@latest
|
|
33
|
+
```
|
|
34
|
+
|
|
35
|
+
### Import in Code
|
|
36
|
+
|
|
37
|
+
```javascript
|
|
38
|
+
const { default: makeWASocket } = require("@hbmodsofc/baileys")
|
|
39
|
+
// or ES6
|
|
40
|
+
import makeWASocket from "@hbmodsofc/baileys"
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
## 🚀 Quick Start
|
|
44
|
+
|
|
45
|
+
### Basic Example
|
|
46
|
+
|
|
47
|
+
```javascript
|
|
48
|
+
const { default: makeWASocket, DisconnectReason, useMultiFileAuthState } = require('@hbmodsofc/baileys')
|
|
49
|
+
const { Boom } = require('@hapi/boom')
|
|
50
|
+
|
|
51
|
+
async function connectToWhatsApp() {
|
|
52
|
+
const { state, saveCreds } = await useMultiFileAuthState('auth_info_hbwabot')
|
|
53
|
+
|
|
54
|
+
const sock = makeWASocket({
|
|
55
|
+
auth: state,
|
|
56
|
+
printQRInTerminal: true,
|
|
57
|
+
browser: ['HBWABot', 'Desktop', '3.0']
|
|
58
|
+
})
|
|
59
|
+
|
|
60
|
+
sock.ev.on('connection.update', (update) => {
|
|
61
|
+
const { connection, lastDisconnect } = update
|
|
62
|
+
if(connection === 'close') {
|
|
63
|
+
const shouldReconnect = (lastDisconnect?.error as Boom)?.output?.statusCode !== DisconnectReason.loggedOut
|
|
64
|
+
console.log('Connection closed due to ', lastDisconnect.error, ', reconnecting ', shouldReconnect)
|
|
65
|
+
if(shouldReconnect) {
|
|
66
|
+
connectToWhatsApp()
|
|
67
|
+
}
|
|
68
|
+
} else if(connection === 'open') {
|
|
69
|
+
console.log('✅ Successfully connected to WhatsApp!')
|
|
70
|
+
}
|
|
71
|
+
})
|
|
72
|
+
|
|
73
|
+
sock.ev.on('messages.upsert', async ({ messages }) => {
|
|
74
|
+
for (const m of messages) {
|
|
75
|
+
if (!m.message) continue
|
|
76
|
+
|
|
77
|
+
console.log('📱 New message:', JSON.stringify(m, undefined, 2))
|
|
78
|
+
|
|
79
|
+
// Balas otomatis
|
|
80
|
+
await sock.sendMessage(m.key.remoteJid!, {
|
|
81
|
+
text: 'Hi! I'm a WhatsApp bot using @hbmodsofc/baileys 🤖'
|
|
82
|
+
})
|
|
83
|
+
}
|
|
84
|
+
})
|
|
85
|
+
|
|
86
|
+
sock.ev.on('creds.update', saveCreds)
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
connectToWhatsApp()
|
|
90
|
+
```
|
|
91
|
+
|
|
92
|
+
## 📋 Table of Contents
|
|
93
|
+
|
|
94
|
+
Disclaimer: This document is still in beta, so there may be errors or inconsistencies.
|
|
95
|
+
|
|
96
|
+
## 🔌 Account Connection
|
|
97
|
+
|
|
98
|
+
WhatsApp provides a multi-device API that allows HBMods-OFC Library to authenticate as a secondary WhatsApp client via a QR code or pairing code.
|
|
99
|
+
|
|
100
|
+
### Connect with QR Code
|
|
101
|
+
|
|
102
|
+
> [!TIP]
|
|
103
|
+
> Customize the browser name using the `Browsers` constant. See the available configurations below.
|
|
104
|
+
|
|
105
|
+
```javascript
|
|
106
|
+
const { default: makeWASocket, Browsers } = require("@hbmodsofc/baileys")
|
|
107
|
+
|
|
108
|
+
const sock = makeWASocket({
|
|
109
|
+
browser: Browsers.ubuntu('My App'),
|
|
110
|
+
printQRInTerminal: true
|
|
111
|
+
})
|
|
112
|
+
```
|
|
113
|
+
|
|
114
|
+
Once the connection is successful, a QR code will appear on the terminal. Scan it with WhatsApp on your phone to log in.
|
|
115
|
+
|
|
116
|
+
### Connect with Pairing Code
|
|
117
|
+
|
|
118
|
+
> [!IMPORTANT]
|
|
119
|
+
> Pairing code is not part of the Mobile API. It allows WhatsApp Web connection without a QR code, but only between one device. See [FAQ WhatsApp](https://faq.whatsapp.com/).
|
|
120
|
+
|
|
121
|
+
Phone numbers must be without `+`, `()`, or `-`, and include the country code.
|
|
122
|
+
|
|
123
|
+
```javascript
|
|
124
|
+
const { default: makeWASocket } = require("@hbmodsofc/baileys")
|
|
125
|
+
|
|
126
|
+
const sock = makeWASocket({
|
|
127
|
+
printQRInTerminal: false
|
|
128
|
+
})
|
|
129
|
+
|
|
130
|
+
// Pairing Normal
|
|
131
|
+
if (!sock.authState.creds.registered) {
|
|
132
|
+
const number = '918416093656'
|
|
133
|
+
const code = await sock.requestPairingCode(number)
|
|
134
|
+
console.log('🔑 Code Pairing:', code)
|
|
135
|
+
}
|
|
136
|
+
|
|
137
|
+
// Pairing Kustom
|
|
138
|
+
if (!sock.authState.creds.registered) {
|
|
139
|
+
const pair = "HBWABOTZ" // 8 character
|
|
140
|
+
const number = '918416093656'
|
|
141
|
+
const code = await sock.requestPairingCode(number, pair)
|
|
142
|
+
console.log('🔑 Code Pairing custom:', code)
|
|
143
|
+
}
|
|
144
|
+
```
|
|
145
|
+
|
|
146
|
+
### Receive Full History
|
|
147
|
+
|
|
148
|
+
1. Set `syncFullHistory` to `true`.
|
|
149
|
+
2. By default, the HBMods-OFC Library uses the Chrome configuration. For desktop-like connections (for more message history)
|
|
150
|
+
|
|
151
|
+
```javascript
|
|
152
|
+
const { default: makeWASocket, Browsers } = require("@hbmodsofc/baileys")
|
|
153
|
+
|
|
154
|
+
const sock = makeWASocket({
|
|
155
|
+
browser: Browsers.macOS('Desktop'),
|
|
156
|
+
syncFullHistory: true
|
|
157
|
+
})
|
|
158
|
+
```
|
|
159
|
+
|
|
160
|
+
## ⚙️ Important Socket Configuration Notes
|
|
161
|
+
|
|
162
|
+
### Group Metadata Caching (Recommended)
|
|
163
|
+
|
|
164
|
+
For group usage, implement group metadata caching:
|
|
165
|
+
|
|
166
|
+
```javascript
|
|
167
|
+
const { default: makeWASocket } = require("@hbmodsofc/baileys")
|
|
168
|
+
const NodeCache = require('node-cache')
|
|
169
|
+
|
|
170
|
+
const groupCache = new NodeCache({ stdTTL: 5 * 60, useClones: false })
|
|
171
|
+
|
|
172
|
+
const sock = makeWASocket({
|
|
173
|
+
cachedGroupMetadata: async (jid) => groupCache.get(jid)
|
|
174
|
+
})
|
|
175
|
+
|
|
176
|
+
sock.ev.on('groups.update', async ([event]) => {
|
|
177
|
+
const metadata = await sock.groupMetadata(event.id)
|
|
178
|
+
groupCache.set(event.id, metadata)
|
|
179
|
+
})
|
|
180
|
+
|
|
181
|
+
sock.ev.on('group-participants.update', async (event) => {
|
|
182
|
+
const metadata = await sock.groupMetadata(event.id)
|
|
183
|
+
groupCache.set(event.id, metadata)
|
|
184
|
+
})
|
|
185
|
+
```
|
|
186
|
+
|
|
187
|
+
### Improve the Vote Poll Retry & Decryption System
|
|
188
|
+
|
|
189
|
+
Improve message delivery and vote poll decryption with the store:
|
|
190
|
+
|
|
191
|
+
```javascript
|
|
192
|
+
const sock = makeWASocket({
|
|
193
|
+
getMessage: async (key) => await getMessageFromStore(key)
|
|
194
|
+
})
|
|
195
|
+
```
|
|
196
|
+
|
|
197
|
+
### Receive Notifications in the WhatsApp App
|
|
198
|
+
|
|
199
|
+
Turn off your online status to receive notifications:
|
|
200
|
+
|
|
201
|
+
```javascript
|
|
202
|
+
const sock = makeWASocket({
|
|
203
|
+
markOnlineOnConnect: false
|
|
204
|
+
})
|
|
205
|
+
```
|
|
206
|
+
|
|
207
|
+
## 💾 Save Auth Info
|
|
208
|
+
|
|
209
|
+
Avoid repeated QR code scanning by saving credentials:
|
|
210
|
+
|
|
211
|
+
```javascript
|
|
212
|
+
const makeWASocket = require("@hbmodsofc/baileys").default
|
|
213
|
+
const { useMultiFileAuthState } = require("@hbmodsofc/baileys")
|
|
214
|
+
|
|
215
|
+
async function connect() {
|
|
216
|
+
const { state, saveCreds } = await useMultiFileAuthState('auth_info_hbwabot')
|
|
217
|
+
const sock = makeWASocket({ auth: state })
|
|
218
|
+
sock.ev.on('creds.update', saveCreds)
|
|
219
|
+
}
|
|
220
|
+
|
|
221
|
+
connect()
|
|
222
|
+
```
|
|
223
|
+
|
|
224
|
+
> [!IMPORTANT]
|
|
225
|
+
> `useMultiFileAuthState` stores the auth state in a folder. For production, use a SQL/No-SQL database and manage key updates carefully.
|
|
226
|
+
|
|
227
|
+
```javascript
|
|
228
|
+
const sock = makeWASocket()
|
|
229
|
+
sock.ev.on('messages.upsert', ({ messages }) => {
|
|
230
|
+
console.log('Dapat pesan:', messages)
|
|
231
|
+
})
|
|
232
|
+
```
|
|
233
|
+
|
|
234
|
+
### Starting Example
|
|
235
|
+
|
|
236
|
+
```javascript
|
|
237
|
+
const makeWASocket = require("@hbmodsofc/baileys").default
|
|
238
|
+
const { DisconnectReason, useMultiFileAuthState } = require("@hbmodsofc/baileys")
|
|
239
|
+
const { Boom } = require('@hapi/boom')
|
|
240
|
+
|
|
241
|
+
async function connectToWhatsApp() {
|
|
242
|
+
const { state, saveCreds } = await useMultiFileAuthState('auth_info_hbwabot')
|
|
243
|
+
const sock = makeWASocket({
|
|
244
|
+
auth: state,
|
|
245
|
+
printQRInTerminal: true
|
|
246
|
+
})
|
|
247
|
+
|
|
248
|
+
sock.ev.on('connection.update', (update) => {
|
|
249
|
+
const { connection, lastDisconnect } = update
|
|
250
|
+
if(connection === 'close') {
|
|
251
|
+
const shouldReconnect = (lastDisconnect.error as Boom)?.output?.statusCode !== DisconnectReason.loggedOut
|
|
252
|
+
console.log('Connection closed due to ', lastDisconnect.error, ', reconnecting ', shouldReconnect)
|
|
253
|
+
if(shouldReconnect) {
|
|
254
|
+
connectToWhatsApp()
|
|
255
|
+
}
|
|
256
|
+
} else if(connection === 'open') {
|
|
257
|
+
console.log('Open connection')
|
|
258
|
+
}
|
|
259
|
+
})
|
|
260
|
+
|
|
261
|
+
sock.ev.on('messages.upsert', async ({ messages }) => {
|
|
262
|
+
for (const m of messages) {
|
|
263
|
+
console.log(JSON.stringify(m, undefined, 2))
|
|
264
|
+
console.log('Balas ke', m.key.remoteJid)
|
|
265
|
+
await sock.sendMessage(m.key.remoteJid!, { text: 'Hello World' })
|
|
266
|
+
}
|
|
267
|
+
})
|
|
268
|
+
|
|
269
|
+
sock.ev.on('creds.update', saveCreds)
|
|
270
|
+
}
|
|
271
|
+
|
|
272
|
+
connectToWhatsApp()
|
|
273
|
+
```
|
|
274
|
+
|
|
275
|
+
### Vote Poll Decryption
|
|
276
|
+
|
|
277
|
+
By default, vote polls are encrypted and handled in `messages.update`:
|
|
278
|
+
|
|
279
|
+
```javascript
|
|
280
|
+
sock.ev.on('messages.update', event => {
|
|
281
|
+
for(const { key, update } of event) {
|
|
282
|
+
if(update.pollUpdates) {
|
|
283
|
+
const pollCreation = await getMessage(key)
|
|
284
|
+
if(pollCreation) {
|
|
285
|
+
console.log(
|
|
286
|
+
'update poll diterima, agregasi: ',
|
|
287
|
+
getAggregateVotesInPollMessage({
|
|
288
|
+
message: pollCreation,
|
|
289
|
+
pollUpdates: update.pollUpdates,
|
|
290
|
+
})
|
|
291
|
+
)
|
|
292
|
+
}
|
|
293
|
+
}
|
|
294
|
+
}
|
|
295
|
+
})
|
|
296
|
+
```
|
|
297
|
+
|
|
298
|
+
`getMessage` is the store implementation (on your end).
|
|
299
|
+
|
|
300
|
+
### First Connection Event Summary
|
|
301
|
+
|
|
302
|
+
1. On the first connection, `connection.update` will be triggered, requesting a restart of the socket.
|
|
303
|
+
2. Then, history messages are received in `messaging.history-set`.
|
|
304
|
+
|
|
305
|
+
## 🗄️ Data Store Implementation
|
|
306
|
+
|
|
307
|
+
The HBMods-OFC Library does not include default storage for chats, contacts, or messages. However, a simple in-memory implementation is provided. The store listens for chat updates, new messages, etc., to keep the data up to date.
|
|
308
|
+
|
|
309
|
+
> [!IMPORTANT]
|
|
310
|
+
> I highly recommend building your own data store, as storing your entire chat history in memory is very RAM intensive.
|
|
311
|
+
|
|
312
|
+
```javascript
|
|
313
|
+
const makeWASocket = require("@hbmodsofc/baileys").default
|
|
314
|
+
const { makeInMemoryStore } = require("@hbmodsofc/baileys")
|
|
315
|
+
|
|
316
|
+
const store = makeInMemoryStore({ })
|
|
317
|
+
|
|
318
|
+
store.readFromFile('./hbwabot_store.json')
|
|
319
|
+
|
|
320
|
+
setInterval(() => {
|
|
321
|
+
store.writeToFile('./hbwabot_store.json')
|
|
322
|
+
}, 10_000)
|
|
323
|
+
|
|
324
|
+
const sock = makeWASocket({ })
|
|
325
|
+
store.bind(sock.ev)
|
|
326
|
+
|
|
327
|
+
sock.ev.on('chats.upsert', () => {
|
|
328
|
+
console.log('can chat', store.chats.all())
|
|
329
|
+
})
|
|
330
|
+
|
|
331
|
+
sock.ev.on('contacts.upsert', () => {
|
|
332
|
+
console.log('can contact', Object.values(store.contacts))
|
|
333
|
+
})
|
|
334
|
+
```
|
|
335
|
+
|
|
336
|
+
The store also provides simple functions like `loadMessages` to speed up data retrieval.
|
|
337
|
+
|
|
338
|
+
## 🆔 WhatsApp ID explanation
|
|
339
|
+
|
|
340
|
+
`ID` is the WhatsApp ID, also called `jid`, for the person or group to whom the message is sent.
|
|
341
|
+
|
|
342
|
+
Format: `[country code][phone number]@s.whatsapp.net`
|
|
343
|
+
Example: `+19999999999@s.whatsapp.net`.
|
|
344
|
+
|
|
345
|
+
For groups: `123456789-123345@g.us`.
|
|
346
|
+
|
|
347
|
+
For broadcast lists: `[creation timestamp]@broadcast`.
|
|
348
|
+
|
|
349
|
+
For story: `status@broadcast`.
|
|
350
|
+
|
|
351
|
+
## 🔧 Utility Functions
|
|
352
|
+
|
|
353
|
+
- `getContentType` - Returns the message content type
|
|
354
|
+
- `getDevice` - Returns the device from the message
|
|
355
|
+
- `makeCacheableSignalKeyStore` - Speeds up store auth
|
|
356
|
+
- `downloadContentFromMessage` - Downloads content from a message
|
|
357
|
+
|
|
358
|
+
## 📤 Send Message
|
|
359
|
+
|
|
360
|
+
Send all types of messages with one function.
|
|
361
|
+
|
|
362
|
+
See supported message content in the section below.
|
|
363
|
+
See options like quotes in the example below.
|
|
364
|
+
|
|
365
|
+
```javascript
|
|
366
|
+
const jid: string
|
|
367
|
+
const content: AnyMessageContent
|
|
368
|
+
const options: MiscMessageGenerationOptions
|
|
369
|
+
|
|
370
|
+
sock.sendMessage(jid, content, options)
|
|
371
|
+
```
|
|
372
|
+
|
|
373
|
+
### Non-Media Messages
|
|
374
|
+
|
|
375
|
+
#### Text Message
|
|
376
|
+
|
|
377
|
+
```javascript
|
|
378
|
+
await sock.sendMessage(jid, { text: 'hello world' })
|
|
379
|
+
```
|
|
380
|
+
|
|
381
|
+
#### Quote Message (works with all types)
|
|
382
|
+
|
|
383
|
+
```javascript
|
|
384
|
+
await sock.sendMessage(jid, { text: 'hello world' }, { quoted: message })
|
|
385
|
+
```
|
|
386
|
+
|
|
387
|
+
#### Name User (works with most types)
|
|
388
|
+
|
|
389
|
+
`@number` for mention in text, optional..
|
|
390
|
+
|
|
391
|
+
```javascript
|
|
392
|
+
await sock.sendMessage(
|
|
393
|
+
jid,
|
|
394
|
+
{
|
|
395
|
+
text: '@12345678901',
|
|
396
|
+
mentions: ['12345678901@s.whatsapp.net']
|
|
397
|
+
}
|
|
398
|
+
)
|
|
399
|
+
```
|
|
400
|
+
|
|
401
|
+
#### Forward Message
|
|
402
|
+
|
|
403
|
+
Requires a message object, retrieve it from the store or use a message object.
|
|
404
|
+
|
|
405
|
+
```javascript
|
|
406
|
+
const msg = getMessageFromStore() // implementasikan sendiri
|
|
407
|
+
await sock.sendMessage(jid, { forward: msg })
|
|
408
|
+
```
|
|
409
|
+
|
|
410
|
+
#### Message Location
|
|
411
|
+
|
|
412
|
+
```javascript
|
|
413
|
+
await sock.sendMessage(
|
|
414
|
+
jid,
|
|
415
|
+
{
|
|
416
|
+
location: {
|
|
417
|
+
degreesLatitude: 24.121231,
|
|
418
|
+
degreesLongitude: 55.1121221
|
|
419
|
+
}
|
|
420
|
+
}
|
|
421
|
+
)
|
|
422
|
+
```
|
|
423
|
+
|
|
424
|
+
#### Contact Message
|
|
425
|
+
|
|
426
|
+
```javascript
|
|
427
|
+
const vcard = 'BEGIN:VCARD\n'
|
|
428
|
+
+ 'VERSION:3.0\n'
|
|
429
|
+
+ 'FN:Jeff Singh\n'
|
|
430
|
+
+ 'ORG:Ashoka Uni;\n'
|
|
431
|
+
+ 'TEL;type=CELL;type=VOICE;waid=911234567890:+91 12345 67890\n'
|
|
432
|
+
+ 'END:VCARD'
|
|
433
|
+
|
|
434
|
+
await sock.sendMessage(
|
|
435
|
+
id,
|
|
436
|
+
{
|
|
437
|
+
contacts: {
|
|
438
|
+
displayName: 'Jeff',
|
|
439
|
+
contacts: [{ vcard }]
|
|
440
|
+
}
|
|
441
|
+
}
|
|
442
|
+
)
|
|
443
|
+
```
|
|
444
|
+
|
|
445
|
+
#### Reaction Message
|
|
446
|
+
|
|
447
|
+
Requires a message key, retrieve it from the store or use a key object.
|
|
448
|
+
|
|
449
|
+
```javascript
|
|
450
|
+
await sock.sendMessage(
|
|
451
|
+
jid,
|
|
452
|
+
{
|
|
453
|
+
react: {
|
|
454
|
+
text: '💖', // clear to delete reaction
|
|
455
|
+
key: message.key
|
|
456
|
+
}
|
|
457
|
+
}
|
|
458
|
+
)
|
|
459
|
+
```
|
|
460
|
+
|
|
461
|
+
#### Message PIN
|
|
462
|
+
|
|
463
|
+
Message key needed.
|
|
464
|
+
|
|
465
|
+
Time:
|
|
466
|
+
|
|
467
|
+
| Time | Seconds |
|
|
468
|
+
|-------|------------|
|
|
469
|
+
| 24h | 86.400 |
|
|
470
|
+
| 7h | 604.800 |
|
|
471
|
+
| 30h | 2.592.000 |
|
|
472
|
+
|
|
473
|
+
```javascript
|
|
474
|
+
await sock.sendMessage(
|
|
475
|
+
jid,
|
|
476
|
+
{
|
|
477
|
+
pin: {
|
|
478
|
+
type: 1, // 0 to delete
|
|
479
|
+
time: 86400,
|
|
480
|
+
key: message.key
|
|
481
|
+
}
|
|
482
|
+
}
|
|
483
|
+
)
|
|
484
|
+
```
|
|
485
|
+
|
|
486
|
+
#### Poll Message
|
|
487
|
+
|
|
488
|
+
```javascript
|
|
489
|
+
await sock.sendMessage(
|
|
490
|
+
jid,
|
|
491
|
+
{
|
|
492
|
+
poll: {
|
|
493
|
+
name: 'My Poll',
|
|
494
|
+
values: ['Option 1', 'Option 2', ...],
|
|
495
|
+
selectableCount: 1,
|
|
496
|
+
toAnnouncementGroup: false // or true
|
|
497
|
+
}
|
|
498
|
+
}
|
|
499
|
+
)
|
|
500
|
+
```
|
|
501
|
+
|
|
502
|
+
### Send with Link Preview
|
|
503
|
+
|
|
504
|
+
1. By default, WhatsApp doesn't generate links from the web.
|
|
505
|
+
2. The HBMods-OFC Library has a link preview function.
|
|
506
|
+
3. Add `link-preview-js` with `npm i link-preview-js`.
|
|
507
|
+
4. Submit the link:
|
|
508
|
+
|
|
509
|
+
```javascript
|
|
510
|
+
await sock.sendMessage(
|
|
511
|
+
jid,
|
|
512
|
+
{
|
|
513
|
+
text: 'Hello, this was sent using https://npmjs.com/@hbmodsofc/baileys'
|
|
514
|
+
}
|
|
515
|
+
)
|
|
516
|
+
```
|
|
517
|
+
|
|
518
|
+
### Media Messages
|
|
519
|
+
|
|
520
|
+
Sending media (videos, stickers, images) is easier and more efficient.
|
|
521
|
+
|
|
522
|
+
> [!NOTE] In media messages, you can use `{ stream: Stream }` or `{ url: Url }` or Buffer directly, see example below.
|
|
523
|
+
|
|
524
|
+
HBMods-OFC Library does not fit the entire buffer into memory; encrypts as a stream.
|
|
525
|
+
|
|
526
|
+
> [!TIP] Use Stream or URL to save memory.
|
|
527
|
+
|
|
528
|
+
#### GIF Message
|
|
529
|
+
|
|
530
|
+
WA does not support .gif, send as .mp4 with the `gifPlayback` flag.
|
|
531
|
+
|
|
532
|
+
```javascript
|
|
533
|
+
await sock.sendMessage(
|
|
534
|
+
jid,
|
|
535
|
+
{
|
|
536
|
+
video: fs.readFileSync('Media/ma_gif.mp4'),
|
|
537
|
+
caption: 'hello world',
|
|
538
|
+
gifPlayback: true
|
|
539
|
+
}
|
|
540
|
+
)
|
|
541
|
+
```
|
|
542
|
+
|
|
543
|
+
#### Video Message
|
|
544
|
+
|
|
545
|
+
```javascript
|
|
546
|
+
await sock.sendMessage(
|
|
547
|
+
id,
|
|
548
|
+
{
|
|
549
|
+
video: {
|
|
550
|
+
url: './Media/ma_gif.mp4'
|
|
551
|
+
},
|
|
552
|
+
caption: 'Hello World',
|
|
553
|
+
ptv: false // true for video notes
|
|
554
|
+
}
|
|
555
|
+
)
|
|
556
|
+
```
|
|
557
|
+
|
|
558
|
+
#### Audio Message
|
|
559
|
+
|
|
560
|
+
Conversion with ffmpeg: `codec: libopus`, `ac: 1`, `avoid_negative_ts`, `make_zero`.
|
|
561
|
+
|
|
562
|
+
Example: `ffmpeg -i input.mp4 -avoid_negative_ts make_zero -ac 1 output.ogg`
|
|
563
|
+
|
|
564
|
+
```javascript
|
|
565
|
+
await sock.sendMessage(
|
|
566
|
+
jid,
|
|
567
|
+
{
|
|
568
|
+
audio: {
|
|
569
|
+
url: './Media/audio.mp3'
|
|
570
|
+
},
|
|
571
|
+
mimetype: 'audio/mp4'
|
|
572
|
+
}
|
|
573
|
+
)
|
|
574
|
+
```
|
|
575
|
+
|
|
576
|
+
#### Image Message
|
|
577
|
+
|
|
578
|
+
```javascript
|
|
579
|
+
await sock.sendMessage(
|
|
580
|
+
id,
|
|
581
|
+
{
|
|
582
|
+
image: {
|
|
583
|
+
url: './Media/ma_img.png'
|
|
584
|
+
},
|
|
585
|
+
caption: 'hello world'
|
|
586
|
+
}
|
|
587
|
+
)
|
|
588
|
+
```
|
|
589
|
+
|
|
590
|
+
#### View Once Messages
|
|
591
|
+
|
|
592
|
+
Add `viewOnce: true` to all the above messages.
|
|
593
|
+
|
|
594
|
+
```javascript
|
|
595
|
+
await sock.sendMessage(
|
|
596
|
+
id,
|
|
597
|
+
{
|
|
598
|
+
image: {
|
|
599
|
+
url: './Media/ma_img.png'
|
|
600
|
+
},
|
|
601
|
+
viewOnce: true, // work with video, audio too
|
|
602
|
+
caption: 'Hello World'
|
|
603
|
+
}
|
|
604
|
+
)
|
|
605
|
+
```
|
|
606
|
+
|
|
607
|
+
## ✏️ Edit Message
|
|
608
|
+
|
|
609
|
+
### Delete Message (for all)
|
|
610
|
+
|
|
611
|
+
```javascript
|
|
612
|
+
const msg = await sock.sendMessage(jid, { text: 'Hello World' })
|
|
613
|
+
await sock.sendMessage(jid, { delete: msg.key })
|
|
614
|
+
```
|
|
615
|
+
|
|
616
|
+
Note: Delete for self support via `chatModify`, see [Modify Chat](#modify-chat).
|
|
617
|
+
|
|
618
|
+
### Edit Message
|
|
619
|
+
|
|
620
|
+
Use editable content.
|
|
621
|
+
|
|
622
|
+
```javascript
|
|
623
|
+
await sock.sendMessage(jid, {
|
|
624
|
+
text: 'updated text here',
|
|
625
|
+
edit: response.key,
|
|
626
|
+
});
|
|
627
|
+
```
|
|
628
|
+
|
|
629
|
+
## 🖼️ Media Message Manipulation
|
|
630
|
+
|
|
631
|
+
### Thumbnails in Media Messages
|
|
632
|
+
|
|
633
|
+
Automatic thumbnails for images & stickers if you add `jimp` or `sharp` (`npm i jimp` or `npm i sharp`).
|
|
634
|
+
|
|
635
|
+
For video, ffmpeg is required.
|
|
636
|
+
|
|
637
|
+
### Download Media Message
|
|
638
|
+
|
|
639
|
+
To save received media:
|
|
640
|
+
|
|
641
|
+
```javascript
|
|
642
|
+
import { createWriteStream } from 'fs'
|
|
643
|
+
import { downloadMediaMessage, getContentType } from '@hbmodsofc/baileys'
|
|
644
|
+
|
|
645
|
+
sock.ev.on('messages.upsert', async ({ messages: [m] }) => {
|
|
646
|
+
if (!m.message) return
|
|
647
|
+
const messageType = getContentType(m)
|
|
648
|
+
|
|
649
|
+
if (messageType === 'imageMessage') {
|
|
650
|
+
const stream = await downloadMediaMessage(
|
|
651
|
+
m,
|
|
652
|
+
'stream', // atau 'buffer'
|
|
653
|
+
{ },
|
|
654
|
+
{
|
|
655
|
+
logger,
|
|
656
|
+
reuploadRequest: sock.updateMediaMessage
|
|
657
|
+
}
|
|
658
|
+
)
|
|
659
|
+
const writeStream = createWriteStream('./my-download.jpeg')
|
|
660
|
+
stream.pipe(writeStream)
|
|
661
|
+
}
|
|
662
|
+
})
|
|
663
|
+
```
|
|
664
|
+
|
|
665
|
+
### Re-upload Media Messages to WhatsApp
|
|
666
|
+
|
|
667
|
+
WA deletes old media from the server. Re-upload using:
|
|
668
|
+
|
|
669
|
+
```javascript
|
|
670
|
+
await sock.updateMediaMessage(msg)
|
|
671
|
+
```
|
|
672
|
+
|
|
673
|
+
## 📞 Reject Call
|
|
674
|
+
|
|
675
|
+
Retrieve `callId` and `callFrom` from the `call` event.
|
|
676
|
+
|
|
677
|
+
```javascript
|
|
678
|
+
await sock.rejectCall(callId, callFrom)
|
|
679
|
+
```
|
|
680
|
+
|
|
681
|
+
## 💬 Send Status in Chat
|
|
682
|
+
|
|
683
|
+
### Read Message
|
|
684
|
+
|
|
685
|
+
The message key set must be explicitly marked read.
|
|
686
|
+
|
|
687
|
+
```javascript
|
|
688
|
+
const key: WAMessageKey
|
|
689
|
+
await sock.readMessages([key]) // can be multiple keys
|
|
690
|
+
```
|
|
691
|
+
|
|
692
|
+
The message ID is a unique identifier. Access it with `message.key.id`.
|
|
693
|
+
|
|
694
|
+
### Attendance Update
|
|
695
|
+
|
|
696
|
+
`presence` bisa: available, composing, recording, paused, unavailable.
|
|
697
|
+
|
|
698
|
+
Valid for 10 seconds. Tell jid whether you are online, offline, typing, etc.
|
|
699
|
+
|
|
700
|
+
```javascript
|
|
701
|
+
await sock.sendPresenceUpdate('available', jid)
|
|
702
|
+
```
|
|
703
|
+
|
|
704
|
+
> [!NOTE] If the desktop client is active, WA does not send push notifications. To receive notifications, set it offline with `sock.sendPresenceUpdate('unavailable')`.
|
|
705
|
+
|
|
706
|
+
## 📁 Change Chat
|
|
707
|
+
|
|
708
|
+
WA uses encrypted communication for chat/app updates.
|
|
709
|
+
|
|
710
|
+
> [!IMPORTANT] If the update is incorrect, WhatsApp may log you out of all devices.
|
|
711
|
+
|
|
712
|
+
### Archive Chats
|
|
713
|
+
|
|
714
|
+
```javascript
|
|
715
|
+
const lastMsgInChat = await getLastMessageInChat(jid) // implement it yourself
|
|
716
|
+
await sock.chatModify({ archive: true, lastMessages: [lastMsgInChat] }, jid)
|
|
717
|
+
```
|
|
718
|
+
|
|
719
|
+
### Mute/Unmute Chat
|
|
720
|
+
|
|
721
|
+
Supported time:
|
|
722
|
+
|
|
723
|
+
| Time | Milliseconds |
|
|
724
|
+
|-------|-------------|
|
|
725
|
+
| Delete | null |
|
|
726
|
+
| 8j | 86.400.000 |
|
|
727
|
+
| 7h | 604.800.000 |
|
|
728
|
+
|
|
729
|
+
```javascript
|
|
730
|
+
// Mute 8 hours
|
|
731
|
+
await sock.chatModify({ mute: 8 * 60 * 60 * 1000 }, jid)
|
|
732
|
+
// Unmute
|
|
733
|
+
await sock.chatModify({ mute: null }, jid)
|
|
734
|
+
```
|
|
735
|
+
|
|
736
|
+
### Mark Chats Read/Unread
|
|
737
|
+
|
|
738
|
+
```javascript
|
|
739
|
+
const lastMsgInChat = await getLastMessageInChat(jid)
|
|
740
|
+
// mark as unread
|
|
741
|
+
await sock.chatModify({ markRead: false, lastMessages: [lastMsgInChat] }, jid)
|
|
742
|
+
```
|
|
743
|
+
|
|
744
|
+
### Delete Message for Me
|
|
745
|
+
|
|
746
|
+
```javascript
|
|
747
|
+
await sock.chatModify(
|
|
748
|
+
{
|
|
749
|
+
clear: {
|
|
750
|
+
messages: [
|
|
751
|
+
{
|
|
752
|
+
id: 'ATWYHDNNWU81732J',
|
|
753
|
+
fromMe: true,
|
|
754
|
+
timestamp: '1654823909'
|
|
755
|
+
}
|
|
756
|
+
]
|
|
757
|
+
}
|
|
758
|
+
},
|
|
759
|
+
jid
|
|
760
|
+
)
|
|
761
|
+
```
|
|
762
|
+
|
|
763
|
+
### Delete Chat
|
|
764
|
+
|
|
765
|
+
```javascript
|
|
766
|
+
const lastMsgInChat = await getLastMessageInChat(jid)
|
|
767
|
+
await sock.chatModify({
|
|
768
|
+
delete: true,
|
|
769
|
+
lastMessages: [
|
|
770
|
+
{
|
|
771
|
+
key: lastMsgInChat.key,
|
|
772
|
+
messageTimestamp: lastMsgInChat.messageTimestamp
|
|
773
|
+
}
|
|
774
|
+
]
|
|
775
|
+
},
|
|
776
|
+
jid
|
|
777
|
+
)
|
|
778
|
+
```
|
|
779
|
+
|
|
780
|
+
### Pin/Unpin Chat
|
|
781
|
+
|
|
782
|
+
```javascript
|
|
783
|
+
await sock.chatModify({
|
|
784
|
+
pin: true // or false to delete pin
|
|
785
|
+
},
|
|
786
|
+
jid
|
|
787
|
+
)
|
|
788
|
+
```
|
|
789
|
+
|
|
790
|
+
### Star/Unstar Messages
|
|
791
|
+
|
|
792
|
+
```javascript
|
|
793
|
+
await sock.chatModify({
|
|
794
|
+
star: {
|
|
795
|
+
messages: [
|
|
796
|
+
{
|
|
797
|
+
id: 'messageID',
|
|
798
|
+
fromMe: true // or false
|
|
799
|
+
}
|
|
800
|
+
],
|
|
801
|
+
star: true // true: Star; false: Unstar
|
|
802
|
+
}
|
|
803
|
+
},
|
|
804
|
+
jid
|
|
805
|
+
)
|
|
806
|
+
```
|
|
807
|
+
|
|
808
|
+
### Disappearing Messages
|
|
809
|
+
|
|
810
|
+
Ephemeral:
|
|
811
|
+
|
|
812
|
+
| Time | Seconds |
|
|
813
|
+
|-------|-------------|
|
|
814
|
+
| Delete | 0 |
|
|
815
|
+
| 24h | 86.400 |
|
|
816
|
+
| 7h | 604.800 |
|
|
817
|
+
| 90h | 7.776.000 |
|
|
818
|
+
|
|
819
|
+
Use seconds, default 7 days.
|
|
820
|
+
|
|
821
|
+
```javascript
|
|
822
|
+
// Enable disappearing messages
|
|
823
|
+
await sock.sendMessage(
|
|
824
|
+
jid,
|
|
825
|
+
{ disappearingMessagesInChat: WA_DEFAULT_EPHEMERAL }
|
|
826
|
+
)
|
|
827
|
+
|
|
828
|
+
// Send as disappearing message
|
|
829
|
+
await sock.sendMessage(jid, { text: 'hello' }, { ephemeralExpiration: WA_DEFAULT_EPHEMERAL })
|
|
830
|
+
|
|
831
|
+
// Turn off
|
|
832
|
+
await sock.sendMessage(
|
|
833
|
+
jid,
|
|
834
|
+
{ disappearingMessagesInChat: false }
|
|
835
|
+
)
|
|
836
|
+
```
|
|
837
|
+
|
|
838
|
+
## 👤 User Query
|
|
839
|
+
|
|
840
|
+
### Check ID Exists on WhatsApp
|
|
841
|
+
|
|
842
|
+
```javascript
|
|
843
|
+
const [result] = await sock.onWhatsApp(jid)
|
|
844
|
+
if (result.exists) console.log(`${jid} is on WhatsApp, as jid: ${result.jid}`)
|
|
845
|
+
```
|
|
846
|
+
|
|
847
|
+
### Query Chat History (groups too)
|
|
848
|
+
|
|
849
|
+
Need the oldest message in a chat.
|
|
850
|
+
|
|
851
|
+
```javascript
|
|
852
|
+
const msg = await getOldestMessageInChat(jid) // implement it yourself
|
|
853
|
+
await sock.fetchMessageHistory(
|
|
854
|
+
50, // jumlah (max: 50 per query)
|
|
855
|
+
msg.key,
|
|
856
|
+
msg.messageTimestamp
|
|
857
|
+
)
|
|
858
|
+
```
|
|
859
|
+
|
|
860
|
+
Message received in `messaging.history-set` event.
|
|
861
|
+
|
|
862
|
+
### Get Status
|
|
863
|
+
|
|
864
|
+
```javascript
|
|
865
|
+
const status = await sock.fetchStatus(jid)
|
|
866
|
+
console.log('status: ' + status)
|
|
867
|
+
```
|
|
868
|
+
|
|
869
|
+
### Take Profile Photo (groups too)
|
|
870
|
+
|
|
871
|
+
```javascript
|
|
872
|
+
// low resolution
|
|
873
|
+
const ppUrl = await sock.profilePictureUrl(jid)
|
|
874
|
+
console.log(ppUrl)
|
|
875
|
+
|
|
876
|
+
// high resolution
|
|
877
|
+
const ppUrl = await sock.profilePictureUrl(jid, 'image')
|
|
878
|
+
```
|
|
879
|
+
|
|
880
|
+
### Get Business Profile (description or category)
|
|
881
|
+
|
|
882
|
+
```javascript
|
|
883
|
+
const profile = await sock.getBusinessProfile(jid)
|
|
884
|
+
console.log('business description: ' + profile.description + ', category: ' + profile.category)
|
|
885
|
+
```
|
|
886
|
+
|
|
887
|
+
### Take Someone's Attendance (typing or online)
|
|
888
|
+
|
|
889
|
+
```javascript
|
|
890
|
+
sock.ev.on('presence.update', console.log)
|
|
891
|
+
|
|
892
|
+
await sock.presenceSubscribe(jid)
|
|
893
|
+
```
|
|
894
|
+
|
|
895
|
+
## 🔄 Change Profile
|
|
896
|
+
|
|
897
|
+
### Change Profile Status
|
|
898
|
+
|
|
899
|
+
```javascript
|
|
900
|
+
await sock.updateProfileStatus('Hello World!')
|
|
901
|
+
```
|
|
902
|
+
|
|
903
|
+
### Change Profile Name
|
|
904
|
+
|
|
905
|
+
```javascript
|
|
906
|
+
await sock.updateProfileName('Your Name')
|
|
907
|
+
```
|
|
908
|
+
|
|
909
|
+
### Change Display Photo (groups too)
|
|
910
|
+
|
|
911
|
+
> [!NOTE] Like media messages, use `{ stream: Stream }` or `{ url: Url }` or Buffer, see [Media Message](#media-message).
|
|
912
|
+
|
|
913
|
+
```javascript
|
|
914
|
+
await sock.updateProfilePicture(jid, { url: './new-profile-picture.jpeg' })
|
|
915
|
+
```
|
|
916
|
+
|
|
917
|
+
### Delete Display Photo (groups too)
|
|
918
|
+
|
|
919
|
+
```javascript
|
|
920
|
+
await sock.removeProfilePicture(jid)
|
|
921
|
+
```
|
|
922
|
+
|
|
923
|
+
## 👥 Groups
|
|
924
|
+
|
|
925
|
+
To change group properties, you must be an admin.
|
|
926
|
+
|
|
927
|
+
### Create a Group
|
|
928
|
+
|
|
929
|
+
```javascript
|
|
930
|
+
const group = await sock.groupCreate('Your Group', ['1234@s.whatsapp.net', '4564@s.whatsapp.net'])
|
|
931
|
+
console.log('groups are created with id: ' + group.gid)
|
|
932
|
+
await sock.sendMessage(group.id, { text: 'hi everybody' })
|
|
933
|
+
```
|
|
934
|
+
|
|
935
|
+
### Add/Delete or Lower/Increase
|
|
936
|
+
|
|
937
|
+
```javascript
|
|
938
|
+
await sock.groupParticipantsUpdate(
|
|
939
|
+
jid,
|
|
940
|
+
['abcd@s.whatsapp.net', 'efgh@s.whatsapp.net'],
|
|
941
|
+
'add' // replace with 'remove', 'demote', or 'promote'
|
|
942
|
+
)
|
|
943
|
+
```
|
|
944
|
+
|
|
945
|
+
### Change Subject (name)
|
|
946
|
+
|
|
947
|
+
```javascript
|
|
948
|
+
await sock.groupUpdateSubject(jid, 'New Subject!')
|
|
949
|
+
```
|
|
950
|
+
|
|
951
|
+
### Change Description
|
|
952
|
+
|
|
953
|
+
```javascript
|
|
954
|
+
await sock.groupUpdateDescription(jid, 'New Description!')
|
|
955
|
+
```
|
|
956
|
+
|
|
957
|
+
### Change Settings
|
|
958
|
+
|
|
959
|
+
```javascript
|
|
960
|
+
// Only admin send messages
|
|
961
|
+
await sock.groupSettingUpdate(jid, 'announcement')
|
|
962
|
+
// Everyone can send
|
|
963
|
+
await sock.groupSettingUpdate(jid, 'not_announcement')
|
|
964
|
+
// Everyone can change group settings
|
|
965
|
+
await sock.groupSettingUpdate(jid, 'unlocked')
|
|
966
|
+
// Only admin change settings
|
|
967
|
+
await sock.groupSettingUpdate(jid, 'locked')
|
|
968
|
+
```
|
|
969
|
+
|
|
970
|
+
### Exit Group
|
|
971
|
+
|
|
972
|
+
```javascript
|
|
973
|
+
await sock.groupLeave(jid)
|
|
974
|
+
```
|
|
975
|
+
|
|
976
|
+
### Get Invitation Code
|
|
977
|
+
|
|
978
|
+
Create link: `'https://chat.whatsapp.com/' + code`.
|
|
979
|
+
|
|
980
|
+
```javascript
|
|
981
|
+
const code = await sock.groupInviteCode(jid)
|
|
982
|
+
console.log('kode grup: ' + code)
|
|
983
|
+
```
|
|
984
|
+
|
|
985
|
+
### Revoke Invitation Code
|
|
986
|
+
|
|
987
|
+
```javascript
|
|
988
|
+
const code = await sock.groupRevokeInvite(jid)
|
|
989
|
+
console.log('New group code: ' + code)
|
|
990
|
+
```
|
|
991
|
+
|
|
992
|
+
### Join Using Invitation Code
|
|
993
|
+
|
|
994
|
+
Code without `https://chat.whatsapp.com/`.
|
|
995
|
+
|
|
996
|
+
```javascript
|
|
997
|
+
const response = await sock.groupAcceptInvite(code)
|
|
998
|
+
console.log('join in: ' + response)
|
|
999
|
+
```
|
|
1000
|
+
|
|
1001
|
+
### Get Group Info from Invitation Code
|
|
1002
|
+
|
|
1003
|
+
```javascript
|
|
1004
|
+
const response = await sock.groupGetInviteInfo(code)
|
|
1005
|
+
console.log('group info: ' + response)
|
|
1006
|
+
```
|
|
1007
|
+
|
|
1008
|
+
### Query Metadata (participant, name, description...)
|
|
1009
|
+
|
|
1010
|
+
```javascript
|
|
1011
|
+
const metadata = await sock.groupMetadata(jid)
|
|
1012
|
+
console.log(metadata.id + ', title: ' + metadata.subject + ', description: ' + metadata.desc)
|
|
1013
|
+
```
|
|
1014
|
+
|
|
1015
|
+
### Join Using groupInviteMessage
|
|
1016
|
+
|
|
1017
|
+
```javascript
|
|
1018
|
+
const response = await sock.groupAcceptInviteV4(jid, groupInviteMessage)
|
|
1019
|
+
console.log('join in: ' + response)
|
|
1020
|
+
```
|
|
1021
|
+
|
|
1022
|
+
### Get Join Request List
|
|
1023
|
+
|
|
1024
|
+
```javascript
|
|
1025
|
+
const response = await sock.groupRequestParticipantsList(jid)
|
|
1026
|
+
console.log(response)
|
|
1027
|
+
```
|
|
1028
|
+
|
|
1029
|
+
### Approve/Decline Join Request
|
|
1030
|
+
|
|
1031
|
+
```javascript
|
|
1032
|
+
const response = await sock.groupRequestParticipantsUpdate(
|
|
1033
|
+
jid,
|
|
1034
|
+
['abcd@s.whatsapp.net', 'efgh@s.whatsapp.net'],
|
|
1035
|
+
'approve' // or 'reject'
|
|
1036
|
+
)
|
|
1037
|
+
console.log(response)
|
|
1038
|
+
```
|
|
1039
|
+
|
|
1040
|
+
### Fetch All Followed Groups Metadata
|
|
1041
|
+
|
|
1042
|
+
```javascript
|
|
1043
|
+
const response = await sock.groupFetchAllParticipating()
|
|
1044
|
+
console.log(response)
|
|
1045
|
+
```
|
|
1046
|
+
|
|
1047
|
+
### Toggle Ephemeral
|
|
1048
|
+
|
|
1049
|
+
Ephemeral:
|
|
1050
|
+
|
|
1051
|
+
| Time | Seconds |
|
|
1052
|
+
|-------|-------------|
|
|
1053
|
+
| Delete | 0 |
|
|
1054
|
+
| 24h | 86.400 |
|
|
1055
|
+
| 7h | 604.800 |
|
|
1056
|
+
| 90h | 7.776.000 |
|
|
1057
|
+
|
|
1058
|
+
```javascript
|
|
1059
|
+
await sock.groupToggleEphemeral(jid, 86400)
|
|
1060
|
+
```
|
|
1061
|
+
|
|
1062
|
+
### Ubah Mode Tambah
|
|
1063
|
+
|
|
1064
|
+
```javascript
|
|
1065
|
+
await sock.groupMemberAddMode(
|
|
1066
|
+
jid,
|
|
1067
|
+
'all_member_add' // or 'admin_add'
|
|
1068
|
+
)
|
|
1069
|
+
```
|
|
1070
|
+
|
|
1071
|
+
## 🔒 Privacy
|
|
1072
|
+
|
|
1073
|
+
### Block/Unblock Users.
|
|
1074
|
+
|
|
1075
|
+
```javascript
|
|
1076
|
+
await sock.updateBlockStatus(jid, 'block') // Block
|
|
1077
|
+
await sock.updateBlockStatus(jid, 'unblock') // Unblock.
|
|
1078
|
+
```
|
|
1079
|
+
|
|
1080
|
+
### Take Privacy Settings
|
|
1081
|
+
|
|
1082
|
+
```javascript
|
|
1083
|
+
const privacySettings = await sock.fetchPrivacySettings(true)
|
|
1084
|
+
console.log('privacy settings: ' + privacySettings)
|
|
1085
|
+
```
|
|
1086
|
+
|
|
1087
|
+
### Get Block List
|
|
1088
|
+
|
|
1089
|
+
```javascript
|
|
1090
|
+
const response = await sock.fetchBlocklist()
|
|
1091
|
+
console.log(response)
|
|
1092
|
+
```
|
|
1093
|
+
|
|
1094
|
+
### Last Seen Privacy Update
|
|
1095
|
+
|
|
1096
|
+
```javascript
|
|
1097
|
+
const value = 'all' // 'contacts' | 'contact_blacklist' | 'none'
|
|
1098
|
+
await sock.updateLastSeenPrivacy(value)
|
|
1099
|
+
```
|
|
1100
|
+
|
|
1101
|
+
### Online Privacy Update
|
|
1102
|
+
|
|
1103
|
+
```javascript
|
|
1104
|
+
const value = 'all' // 'match_last_seen'
|
|
1105
|
+
await sock.updateOnlinePrivacy(value)
|
|
1106
|
+
```
|
|
1107
|
+
|
|
1108
|
+
### Profile Photo Privacy Update
|
|
1109
|
+
|
|
1110
|
+
```javascript
|
|
1111
|
+
const value = 'all' // 'contacts' | 'contact_blacklist' | 'none'
|
|
1112
|
+
await sock.updateProfilePicturePrivacy(value)
|
|
1113
|
+
```
|
|
1114
|
+
|
|
1115
|
+
### Update Privacy Status
|
|
1116
|
+
|
|
1117
|
+
```javascript
|
|
1118
|
+
const value = 'all' // 'contacts' | 'contact_blacklist' | 'none'
|
|
1119
|
+
await sock.updateStatusPrivacy(value)
|
|
1120
|
+
```
|
|
1121
|
+
|
|
1122
|
+
### Read Receipt Privacy Update
|
|
1123
|
+
|
|
1124
|
+
```javascript
|
|
1125
|
+
const value = 'all' // 'none'
|
|
1126
|
+
await sock.updateReadReceiptsPrivacy(value)
|
|
1127
|
+
```
|
|
1128
|
+
|
|
1129
|
+
### Update Privacy Add Group
|
|
1130
|
+
|
|
1131
|
+
```javascript
|
|
1132
|
+
const value = 'all' // 'contacts' | 'contact_blacklist'
|
|
1133
|
+
await sock.updateGroupsAddPrivacy(value)
|
|
1134
|
+
```
|
|
1135
|
+
|
|
1136
|
+
### Update Default Disappearance Mode
|
|
1137
|
+
|
|
1138
|
+
Ephemeral:
|
|
1139
|
+
|
|
1140
|
+
| Time | Seconds |
|
|
1141
|
+
|-------|-------------|
|
|
1142
|
+
| Delete | 0 |
|
|
1143
|
+
| 24h | 86.400 |
|
|
1144
|
+
| 7h | 604.800 |
|
|
1145
|
+
| 90h | 7.776.000 |
|
|
1146
|
+
|
|
1147
|
+
```javascript
|
|
1148
|
+
const ephemeral = 86400
|
|
1149
|
+
await sock.updateDefaultDisappearingMode(ephemeral)
|
|
1150
|
+
```
|
|
1151
|
+
|
|
1152
|
+
## 📢 Broadcast & Story List
|
|
1153
|
+
|
|
1154
|
+
### Send Broadcast & Story
|
|
1155
|
+
|
|
1156
|
+
Messages can be sent to broadcasts and stories. Add a message option:
|
|
1157
|
+
|
|
1158
|
+
```javascript
|
|
1159
|
+
await sock.sendMessage(
|
|
1160
|
+
jid,
|
|
1161
|
+
{
|
|
1162
|
+
image: {
|
|
1163
|
+
url: url
|
|
1164
|
+
},
|
|
1165
|
+
caption: caption
|
|
1166
|
+
},
|
|
1167
|
+
{
|
|
1168
|
+
backgroundColor: backgroundColor,
|
|
1169
|
+
font: font,
|
|
1170
|
+
statusJidList: statusJidList,
|
|
1171
|
+
broadcast: true
|
|
1172
|
+
}
|
|
1173
|
+
)
|
|
1174
|
+
```
|
|
1175
|
+
|
|
1176
|
+
The message body can be `extendedTextMessage`, `imageMessage`, etc., see [Media Message](#media-message).
|
|
1177
|
+
|
|
1178
|
+
`broadcast: true` enables broadcast mode.
|
|
1179
|
+
|
|
1180
|
+
`statusJidList`: list of recipients.
|
|
1181
|
+
|
|
1182
|
+
Broadcast ID: `12345678@broadcast`.
|
|
1183
|
+
|
|
1184
|
+
### Query Receiver & Broadcast List Name
|
|
1185
|
+
|
|
1186
|
+
```javascript
|
|
1187
|
+
const bList = await sock.getBroadcastListInfo('1234@broadcast')
|
|
1188
|
+
console.log(`list name: ${bList.name}, recipient: ${bList.recipients}`)
|
|
1189
|
+
```
|
|
1190
|
+
|
|
1191
|
+
## 🛠️ Custom Functions
|
|
1192
|
+
|
|
1193
|
+
The HBMods-OFC Library is designed for custom functions. Add your own extensions without forking.
|
|
1194
|
+
|
|
1195
|
+
### Enable Debug Level in HBWABot Logs
|
|
1196
|
+
|
|
1197
|
+
```javascript
|
|
1198
|
+
const sock = makeWASocket({
|
|
1199
|
+
logger: P({ level: 'debug' }),
|
|
1200
|
+
})
|
|
1201
|
+
```
|
|
1202
|
+
|
|
1203
|
+
It displays WhatsApp messages in the console.
|
|
1204
|
+
|
|
1205
|
+
### How WhatsApp Communicates
|
|
1206
|
+
|
|
1207
|
+
> [!TIP] Learn WhatsApp protocols with Libsignal Protocol and Noise Protocol.
|
|
1208
|
+
|
|
1209
|
+
Example: Track phone battery percentage. Enable log, battery message appears:
|
|
1210
|
+
|
|
1211
|
+
```json
|
|
1212
|
+
{
|
|
1213
|
+
"level": 10,
|
|
1214
|
+
"fromMe": false,
|
|
1215
|
+
"frame": {
|
|
1216
|
+
"tag": "ib",
|
|
1217
|
+
"attrs": {
|
|
1218
|
+
"from": "@s.whatsapp.net"
|
|
1219
|
+
},
|
|
1220
|
+
"content": [
|
|
1221
|
+
{
|
|
1222
|
+
"tag": "edge_routing",
|
|
1223
|
+
"attrs": {},
|
|
1224
|
+
"content": [
|
|
1225
|
+
{
|
|
1226
|
+
"tag": "routing_info",
|
|
1227
|
+
"attrs": {},
|
|
1228
|
+
"content": {
|
|
1229
|
+
"type": "Buffer",
|
|
1230
|
+
"data": [8,2,8,5]
|
|
1231
|
+
}
|
|
1232
|
+
}
|
|
1233
|
+
]
|
|
1234
|
+
}
|
|
1235
|
+
]
|
|
1236
|
+
},
|
|
1237
|
+
"msg":"communication"
|
|
1238
|
+
}
|
|
1239
|
+
```
|
|
1240
|
+
|
|
1241
|
+
`'frame'` has: `tag` (frame type), `attrs` (metadata), `content` (data).
|
|
1242
|
+
|
|
1243
|
+
### Register Callbacks for Websocket Events
|
|
1244
|
+
|
|
1245
|
+
> [!TIP] See the `onMessageReceived` function in `socket.ts`.
|
|
1246
|
+
|
|
1247
|
+
```javascript
|
|
1248
|
+
// For tags 'edge_routing'
|
|
1249
|
+
sock.ws.on('CB:edge_routing', (node: BinaryNode) => { })
|
|
1250
|
+
|
|
1251
|
+
// With id 'abcd'
|
|
1252
|
+
sock.ws.on('CB:edge_routing,id:abcd', (node: BinaryNode) => { })
|
|
1253
|
+
|
|
1254
|
+
// With node routing_info
|
|
1255
|
+
sock.ws.on('CB:edge_routing,id:abcd,routing_info', (node: BinaryNode) => { })
|
|
1256
|
+
```
|
|
1257
|
+
|
|
1258
|
+
## 💡 Tips & Best Practices
|
|
1259
|
+
|
|
1260
|
+
- **Use Caching**: Cache group metadata for better performance.
|
|
1261
|
+
- **Handle Reconnection**: Implement auto-reconnect for stability.
|
|
1262
|
+
- **Manage Store**: Use a database (MongoDB, PostgreSQL) for production.
|
|
1263
|
+
- **Error Handling**: Wrap socket calls with try-catch.
|
|
1264
|
+
- **Rate Limits**: Respect WhatsApp's limits to avoid bans—don't spam.
|
|
1265
|
+
- **Security**: Don't share auth credentials; use environment variables.
|
|
1266
|
+
|
|
1267
|
+
## 📄 License
|
|
1268
|
+
|
|
1269
|
+
Distributed under the GPL-3.0 License. See [LICENSE](LICENSE) for more information.
|
|
1270
|
+
|
|
1271
|
+
---
|
|
1272
|
+
|
|
1273
|
+
<div align="center">
|
|
1274
|
+
Forked and modified by the HBMods-OFC.
|
|
1275
|
+
Baileys - Modern WhatsApp Web API with @lid to @pn Improvements
|
|
1276
|
+
</div>
|