devstok commited on
Commit
6f55a1e
·
verified ·
1 Parent(s): f54351e

Upload folder using huggingface_hub

Browse files
This view is limited to 50 files because it contains too many changes.   See raw diff
Dockerfile ADDED
@@ -0,0 +1,39 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ # Menggunakan Node.js versi 18 sebagai base image
2
+ FROM node:18
3
+
4
+ # Menginstal git, ffmpeg, imagemagick, dan webp
5
+ RUN apt-get update && \
6
+ apt-get install -y \
7
+ git \
8
+ ffmpeg \
9
+ imagemagick \
10
+ webp && \
11
+ apt-get clean && \
12
+ rm -rf /var/lib/apt/lists/*
13
+
14
+ # Menetapkan direktori kerja
15
+ WORKDIR /app
16
+
17
+ # Membuat direktori sessions
18
+ RUN mkdir -p /app/sessions
19
+
20
+ # Menyalin file package.json dan package-lock.json
21
+ COPY package.json ./
22
+
23
+ # Menginstal dependensi Node.js
24
+ RUN npm install
25
+
26
+ # Menyalin semua file aplikasi ke dalam container
27
+ COPY . .
28
+
29
+ # Mengubah kepemilikan direktori /app
30
+ RUN chown -R node:node /app
31
+
32
+ # Beralih ke pengguna non-root
33
+ USER node
34
+
35
+ # Mengekspos port 7860
36
+ EXPOSE 7860
37
+
38
+ # Menjalankan aplikasi
39
+ CMD ["npm", "start"]
Procfile ADDED
@@ -0,0 +1 @@
 
 
1
+ worker: node index.js --autocleartmp --autoread
README.md CHANGED
@@ -1,12 +1,10 @@
1
  ---
2
- title: Projek2
3
- emoji: 🌍
4
- colorFrom: gray
5
- colorTo: red
6
- sdk: gradio
7
- sdk_version: 5.8.0
8
- app_file: app.py
9
  pinned: false
10
  ---
11
 
12
- Check out the configuration reference at https://huggingface.co/docs/hub/spaces-config-reference
 
1
  ---
2
+ title: veila
3
+ emoji: 😻
4
+ colorFrom: red
5
+ colorTo: indigo
6
+ sdk: docker
 
 
7
  pinned: false
8
  ---
9
 
10
+ Check out the configuration reference at https://huggingface.co/docs/hub/spaces-config-reference
config.js ADDED
@@ -0,0 +1,45 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ global.owner = ['6285878836361']
2
+ global.mods = ['6285878836361']
3
+ global.prems = ['6285878836361']
4
+ global.nameowner = 'rizki'
5
+ global.numberowner = '6285878836361'
6
+ global.mail = 'irfanwibu88@gmail.com'
7
+ global.gc = 'https://chat.whatsapp.com/KIcqnzY4NJMHXPTz8Xopvd'
8
+ global.instagram = 'https://instagram.com/ikykunnnn'
9
+ global.wm = '© ikyyBot Whatsapp Multi device'
10
+ global.wait = '_*Tunggu sedang di proses...*_'
11
+ global.eror = '_*Server Error*_'
12
+ global.stiker_wait = '*⫹⫺ Stiker sedang dibuat...*'
13
+ global.packname = 'Made With'
14
+ global.author = 'Bot WhatsApp'
15
+ global.autobio = true // Set true untuk mengaktifkan autobio
16
+ global.maxwarn = '3' // Peringatan maksimum
17
+ global.antiporn = true // Auto delete pesan porno (bot harus admin)
18
+
19
+ //INI WAJIB DI ISI!//
20
+ global.btc = 'BohqrvbJ'
21
+ //Daftar terlebih dahulu https://api.botcahx.eu.org
22
+
23
+ //INI OPTIONAL BOLEH DI ISI BOLEH JUGA ENGGA//
24
+ global.lann = 'YOUR_APIKEY_HERE'
25
+ //Daftar https://api.betabotz.eu.org
26
+
27
+ //jangan diganti!
28
+ global.APIs = {
29
+ btc: 'https://api.botcahx.eu.org'
30
+ }
31
+
32
+ //ini tidak di isi juga tidak apa-apa
33
+ global.APIKeys = {
34
+ 'https://api.botcahx.eu.org': 'BohqrvbJ'
35
+ }
36
+
37
+ let fs = require('fs')
38
+ let chalk = require('chalk')
39
+ let file = require.resolve(__filename)
40
+ fs.watchFile(file, () => {
41
+ fs.unwatchFile(file)
42
+ console.log(chalk.redBright("Update 'config.js'"))
43
+ delete require.cache[file]
44
+ require(file)
45
+ })
database.json ADDED
@@ -0,0 +1,1734 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ {
2
+ "users": {
3
+ "6285878836361@s.whatsapp.net": {
4
+ "taxi": 0,
5
+ "lasttaxi": 0,
6
+ "lastyoutuber": 0,
7
+ "subscribers": 0,
8
+ "viewers": 0,
9
+ "like": 0,
10
+ "playButton": 0,
11
+ "saldo": 0,
12
+ "pengeluaran": 0,
13
+ "healt": 100,
14
+ "health": 100,
15
+ "energi": 100,
16
+ "power": 100,
17
+ "title": 0,
18
+ "haus": 100,
19
+ "laper": 100,
20
+ "tprem": 0,
21
+ "stamina": 100,
22
+ "level": 0,
23
+ "follow": 0,
24
+ "lastfollow": 0,
25
+ "followers": 0,
26
+ "pasangan": "",
27
+ "sahabat": "",
28
+ "location": "Gubuk",
29
+ "titlein": "Belum Ada",
30
+ "ultah": "",
31
+ "waifu": "Belum Di Set",
32
+ "husbu": "Belum Di Set",
33
+ "pc": 0,
34
+ "exp": 116,
35
+ "coin": 0,
36
+ "atm": 0,
37
+ "limit": 100,
38
+ "skata": 0,
39
+ "tigame": 999,
40
+ "lastclaim": 0,
41
+ "judilast": 0,
42
+ "lastnambang": 0,
43
+ "lastnebang": 0,
44
+ "lastmulung": 0,
45
+ "lastkerja": 0,
46
+ "lastmaling": 0,
47
+ "lastbunuhi": 0,
48
+ "lastbisnis": 0,
49
+ "lastberbisnis": 0,
50
+ "bisnis": 0,
51
+ "berbisnis": 0,
52
+ "lastmancing": 0,
53
+ "pancing": 0,
54
+ "pancingan": 0,
55
+ "totalPancingan": 0,
56
+ "kardus": 0,
57
+ "botol": 0,
58
+ "kaleng": 0,
59
+ "money": 0,
60
+ "litecoin": 0,
61
+ "chip": 0,
62
+ "tiketcoin": 0,
63
+ "poin": 0,
64
+ "bank": 0,
65
+ "balance": 0,
66
+ "diamond": 0,
67
+ "emerald": 0,
68
+ "rock": 0,
69
+ "wood": 0,
70
+ "berlian": 0,
71
+ "iron": 0,
72
+ "emas": 0,
73
+ "common": 0,
74
+ "uncommon": 0,
75
+ "mythic": 0,
76
+ "legendary": 0,
77
+ "rumahsakit": 0,
78
+ "tambang": 0,
79
+ "camptroops": 0,
80
+ "pertanian": 0,
81
+ "fortress": 0,
82
+ "trofi": 0,
83
+ "rtrofi": "perunggu",
84
+ "makanan": 0,
85
+ "troopcamp": 0,
86
+ "shield": 0,
87
+ "arlok": 0,
88
+ "ojekk": 0,
89
+ "ojek": 0,
90
+ "lastngewe": 0,
91
+ "ngewe": 0,
92
+ "polisi": 0,
93
+ "pedagang": 0,
94
+ "dokter": 0,
95
+ "petani": 0,
96
+ "montir": 0,
97
+ "kuli": 0,
98
+ "korbanngocok": 0,
99
+ "coal": 0,
100
+ "korekapi": 0,
101
+ "ayambakar": 0,
102
+ "gulai": 0,
103
+ "rendang": 0,
104
+ "ayamgoreng": 0,
105
+ "oporayam": 0,
106
+ "steak": 0,
107
+ "babipanggang": 0,
108
+ "ikanbakar": 0,
109
+ "lelebakar": 0,
110
+ "nilabakar": 0,
111
+ "bawalbakar": 0,
112
+ "udangbakar": 0,
113
+ "pausbakar": 0,
114
+ "kepitingbakar": 0,
115
+ "soda": 0,
116
+ "vodka": 0,
117
+ "ganja": 0,
118
+ "bandage": 0,
119
+ "sushi": 0,
120
+ "roti": 0,
121
+ "ramuan": 0,
122
+ "lastramuanclaim": 0,
123
+ "gems": 0,
124
+ "cupon": 0,
125
+ "lastgemsclaim": 0,
126
+ "eleksirb": 0,
127
+ "penduduk": 0,
128
+ "archer": 0,
129
+ "shadow": 0,
130
+ "laststringclaim": 0,
131
+ "lastpotionclaim": 0,
132
+ "lastswordclaim": 0,
133
+ "lastweaponclaim": 0,
134
+ "lastironclaim": 0,
135
+ "lastmancingclaim": 0,
136
+ "anakpancingan": 0,
137
+ "as": 0,
138
+ "paus": 0,
139
+ "kepiting": 0,
140
+ "gurita": 0,
141
+ "cumi": 0,
142
+ "buntal": 0,
143
+ "dory": 0,
144
+ "lumba": 0,
145
+ "lobster": 0,
146
+ "hiu": 0,
147
+ "lele": 0,
148
+ "nila": 0,
149
+ "bawal": 0,
150
+ "udang": 0,
151
+ "ikan": 0,
152
+ "orca": 0,
153
+ "banteng": 0,
154
+ "harimau": 0,
155
+ "gajah": 0,
156
+ "kambing": 0,
157
+ "panda": 0,
158
+ "buaya": 0,
159
+ "kerbau": 0,
160
+ "sapi": 0,
161
+ "monyet": 0,
162
+ "babihutan": 0,
163
+ "babi": 0,
164
+ "ayam": 0,
165
+ "apel": 20,
166
+ "ayamb": 0,
167
+ "ayamg": 0,
168
+ "ssapi": 0,
169
+ "sapir": 0,
170
+ "leleb": 0,
171
+ "leleg": 0,
172
+ "esteh": 0,
173
+ "pet": 0,
174
+ "potion": 0,
175
+ "sampah": 0,
176
+ "kucing": 0,
177
+ "kucinglastclaim": 0,
178
+ "kucingexp": 0,
179
+ "kuda": 0,
180
+ "kudalastclaim": 0,
181
+ "rubah": 0,
182
+ "rubahlastclaim": 0,
183
+ "rubahexp": 0,
184
+ "anjing": 0,
185
+ "anjinglastclaim": 0,
186
+ "anjingexp": 0,
187
+ "naga": 0,
188
+ "nagalastclaim": 0,
189
+ "griffin": 0,
190
+ "griffinlastclaim": 0,
191
+ "centaur": 0,
192
+ "fightnaga": 0,
193
+ "centaurlastclaim": 0,
194
+ "serigala": 0,
195
+ "serigalalastclaim": 0,
196
+ "serigalaexp": 0,
197
+ "phonix": 0,
198
+ "phonixlastclaim": 0,
199
+ "phonixexp": 0,
200
+ "makanannaga": 0,
201
+ "makananphonix": 0,
202
+ "makanancentaur": 0,
203
+ "makananserigala": 0,
204
+ "Banneduser": false,
205
+ "BannedReason": "",
206
+ "banned": false,
207
+ "bannedTime": 0,
208
+ "warn": 0,
209
+ "afk": -1,
210
+ "afkReason": "",
211
+ "anakkucing": 0,
212
+ "anakkuda": 0,
213
+ "anakrubah": 0,
214
+ "anakanjing": 0,
215
+ "makananpet": 0,
216
+ "makananPet": 0,
217
+ "antispam": 0,
218
+ "antispamlastclaim": 0,
219
+ "kayu": 0,
220
+ "batu": 0,
221
+ "string": 0,
222
+ "umpan": 0,
223
+ "armor": 0,
224
+ "armordurability": 0,
225
+ "weapon": 0,
226
+ "weapondurability": 0,
227
+ "sword": 0,
228
+ "sworddurability": 0,
229
+ "pickaxe": 0,
230
+ "pickaxedurability": 0,
231
+ "fishingrod": 0,
232
+ "fishingroddurability": 0,
233
+ "katana": 0,
234
+ "katanadurability": 0,
235
+ "bow": 0,
236
+ "bowdurability": 0,
237
+ "kapak": 0,
238
+ "kapakdurability": 0,
239
+ "axe": 0,
240
+ "axedurability": 0,
241
+ "pisau": 0,
242
+ "pisaudurability": 0,
243
+ "kerjasatu": 0,
244
+ "kerjadua": 0,
245
+ "kerjatiga": 0,
246
+ "kerjaempat": 0,
247
+ "kerjalima": 0,
248
+ "kerjaenam": 0,
249
+ "kerjatujuh": 0,
250
+ "kerjadelapan": 0,
251
+ "kerjasembilan": 0,
252
+ "kerjasepuluh": 0,
253
+ "kerjasebelas": 0,
254
+ "kerjaduabelas": 0,
255
+ "kerjatigabelas": 0,
256
+ "kerjaempatbelas": 0,
257
+ "kerjalimabelas": 0,
258
+ "pekerjaansatu": 0,
259
+ "pekerjaandua": 0,
260
+ "pekerjaantiga": 0,
261
+ "pekerjaanempat": 0,
262
+ "pekerjaanlima": 0,
263
+ "pekerjaanenam": 0,
264
+ "pekerjaantujuh": 0,
265
+ "pekerjaandelapan": 0,
266
+ "pekerjaansembilan": 0,
267
+ "pekerjaansepuluh": 0,
268
+ "pekerjaansebelas": 0,
269
+ "pekerjaanduabelas": 0,
270
+ "pekerjaantigabelas": 0,
271
+ "pekerjaanempatbelas": 0,
272
+ "pekerjaanlimabelas": 0,
273
+ "lastadventure": 0,
274
+ "lastwar": 0,
275
+ "lastberkebon": 0,
276
+ "lastberburu": 0,
277
+ "lastbansos": 0,
278
+ "lastrampok": 0,
279
+ "lastkill": 0,
280
+ "lastfishing": 0,
281
+ "lastdungeon": 0,
282
+ "lastduel": 0,
283
+ "lastmining": 0,
284
+ "lasthourly": 0,
285
+ "lastdagang": 0,
286
+ "lasthunt": 0,
287
+ "lasthun": 0,
288
+ "lastweekly": 0,
289
+ "lastmonthly": 0,
290
+ "lastyearly": 0,
291
+ "lastjb": 0,
292
+ "lastrob": 0,
293
+ "lastdaang": 0,
294
+ "lastngojek": 0,
295
+ "lastgrab": 0,
296
+ "lastngocok": 0,
297
+ "lastturu": 0,
298
+ "lastseen": 0,
299
+ "lastSetStatus": 0,
300
+ "registered": false,
301
+ "mangga": 0,
302
+ "stroberi": 0,
303
+ "semangka": 0,
304
+ "jeruk": 0,
305
+ "name": "+62 858-7883-6361",
306
+ "age": -1,
307
+ "regTime": -1,
308
+ "premiumDate": -1,
309
+ "premium": false,
310
+ "premiumTime": 0,
311
+ "vip": "tidak",
312
+ "vipPoin": 0,
313
+ "job": "Pengangguran",
314
+ "jobexp": 0,
315
+ "jail": false,
316
+ "penjara": false,
317
+ "antarpaket": 0,
318
+ "dirawat": false,
319
+ "lbars": "[▒▒▒▒▒▒▒▒▒]",
320
+ "role": "Newbie ㋡",
321
+ "autolevelup": true,
322
+ "lastIstigfar": 0,
323
+ "skill": "",
324
+ "korps": "",
325
+ "korpsgrade": "",
326
+ "demon": "",
327
+ "breaths": "",
328
+ "magic": "",
329
+ "darahiblis": 0,
330
+ "demonblood": 0,
331
+ "demonkill": 0,
332
+ "hashirakill": 0,
333
+ "alldemonkill": 0,
334
+ "allhashirakill": 0,
335
+ "attack": 0,
336
+ "speed": 0,
337
+ "strenght": 0,
338
+ "defense": 0,
339
+ "regeneration": 0,
340
+ "ovo": 0,
341
+ "dana": 0,
342
+ "gopay": 0,
343
+ "lastngaji": 0,
344
+ "lastlonte": 0,
345
+ "lastkoboy": 0,
346
+ "lastdate": 0,
347
+ "lasttambang": 0,
348
+ "lastngepet": 0,
349
+ "command": 2,
350
+ "commandTotal": 2,
351
+ "lastCmd": 1733916892180,
352
+ "glimit": 10,
353
+ "pertambangan": 0,
354
+ "lastbossbattle": 0,
355
+ "aqua": 0,
356
+ "glory": 0,
357
+ "enchant": 0,
358
+ "psepick": 0,
359
+ "psenjata": 0,
360
+ "lastgemclaim": 0,
361
+ "makanangriffin": 0,
362
+ "healthmonster": 0,
363
+ "anakserigala": 0,
364
+ "anaknaga": 0,
365
+ "anakphonix": 0,
366
+ "anakgriffin": 0,
367
+ "kyubi": 0,
368
+ "anakkyubi": 0,
369
+ "anakcentaur": 0,
370
+ "kingdom": false,
371
+ "lastsda": 0,
372
+ "lastberbru": 0,
373
+ "lastgift": 0,
374
+ "jualan": 0,
375
+ "lastjualan": 0,
376
+ "ngocokk": 0,
377
+ "lastngocokk": 0,
378
+ "lastcodereg": 0,
379
+ "anggur": 0,
380
+ "pisang": 0,
381
+ "bibitanggur": 0,
382
+ "bibitpisang": 0,
383
+ "bibitapel": 0,
384
+ "bibitmangga": 0,
385
+ "bibitjeruk": 0
386
+ },
387
+ "6283121935164@s.whatsapp.net": {
388
+ "taxi": 0,
389
+ "lasttaxi": 0,
390
+ "lastyoutuber": 0,
391
+ "subscribers": 0,
392
+ "viewers": 0,
393
+ "like": 0,
394
+ "playButton": 0,
395
+ "saldo": 0,
396
+ "pengeluaran": 0,
397
+ "healt": 100,
398
+ "health": 100,
399
+ "energi": 100,
400
+ "power": 100,
401
+ "title": 0,
402
+ "haus": 100,
403
+ "laper": 100,
404
+ "tprem": 0,
405
+ "stamina": 100,
406
+ "level": 0,
407
+ "follow": 0,
408
+ "lastfollow": 0,
409
+ "followers": 0,
410
+ "pasangan": "",
411
+ "sahabat": "",
412
+ "location": "Gubuk",
413
+ "titlein": "Belum Ada",
414
+ "ultah": "",
415
+ "waifu": "Belum Di Set",
416
+ "husbu": "Belum Di Set",
417
+ "pc": 0,
418
+ "exp": 0,
419
+ "coin": 0,
420
+ "atm": 0,
421
+ "limit": 100,
422
+ "skata": 0,
423
+ "tigame": 999,
424
+ "lastclaim": 0,
425
+ "judilast": 0,
426
+ "lastnambang": 0,
427
+ "lastnebang": 0,
428
+ "lastmulung": 0,
429
+ "lastkerja": 0,
430
+ "lastmaling": 0,
431
+ "lastbunuhi": 0,
432
+ "lastbisnis": 0,
433
+ "lastberbisnis": 0,
434
+ "bisnis": 0,
435
+ "berbisnis": 0,
436
+ "lastmancing": 0,
437
+ "pancing": 0,
438
+ "pancingan": 0,
439
+ "totalPancingan": 0,
440
+ "kardus": 0,
441
+ "botol": 0,
442
+ "kaleng": 0,
443
+ "money": 0,
444
+ "litecoin": 0,
445
+ "chip": 0,
446
+ "tiketcoin": 0,
447
+ "poin": 0,
448
+ "bank": 0,
449
+ "balance": 0,
450
+ "diamond": 0,
451
+ "emerald": 0,
452
+ "rock": 0,
453
+ "wood": 0,
454
+ "berlian": 0,
455
+ "iron": 0,
456
+ "emas": 0,
457
+ "common": 0,
458
+ "uncommon": 0,
459
+ "mythic": 0,
460
+ "legendary": 0,
461
+ "rumahsakit": 0,
462
+ "tambang": 0,
463
+ "camptroops": 0,
464
+ "pertanian": 0,
465
+ "fortress": 0,
466
+ "trofi": 0,
467
+ "rtrofi": "perunggu",
468
+ "makanan": 0,
469
+ "troopcamp": 0,
470
+ "shield": 0,
471
+ "arlok": 0,
472
+ "ojekk": 0,
473
+ "ojek": 0,
474
+ "lastngewe": 0,
475
+ "ngewe": 0,
476
+ "polisi": 0,
477
+ "pedagang": 0,
478
+ "dokter": 0,
479
+ "petani": 0,
480
+ "montir": 0,
481
+ "kuli": 0,
482
+ "korbanngocok": 0,
483
+ "coal": 0,
484
+ "korekapi": 0,
485
+ "ayambakar": 0,
486
+ "gulai": 0,
487
+ "rendang": 0,
488
+ "ayamgoreng": 0,
489
+ "oporayam": 0,
490
+ "steak": 0,
491
+ "babipanggang": 0,
492
+ "ikanbakar": 0,
493
+ "lelebakar": 0,
494
+ "nilabakar": 0,
495
+ "bawalbakar": 0,
496
+ "udangbakar": 0,
497
+ "pausbakar": 0,
498
+ "kepitingbakar": 0,
499
+ "soda": 0,
500
+ "vodka": 0,
501
+ "ganja": 0,
502
+ "bandage": 0,
503
+ "sushi": 0,
504
+ "roti": 0,
505
+ "ramuan": 0,
506
+ "lastramuanclaim": 0,
507
+ "gems": 0,
508
+ "cupon": 0,
509
+ "lastgemsclaim": 0,
510
+ "eleksirb": 0,
511
+ "penduduk": 0,
512
+ "archer": 0,
513
+ "shadow": 0,
514
+ "laststringclaim": 0,
515
+ "lastpotionclaim": 0,
516
+ "lastswordclaim": 0,
517
+ "lastweaponclaim": 0,
518
+ "lastironclaim": 0,
519
+ "lastmancingclaim": 0,
520
+ "anakpancingan": 0,
521
+ "as": 0,
522
+ "paus": 0,
523
+ "kepiting": 0,
524
+ "gurita": 0,
525
+ "cumi": 0,
526
+ "buntal": 0,
527
+ "dory": 0,
528
+ "lumba": 0,
529
+ "lobster": 0,
530
+ "hiu": 0,
531
+ "lele": 0,
532
+ "nila": 0,
533
+ "bawal": 0,
534
+ "udang": 0,
535
+ "ikan": 0,
536
+ "orca": 0,
537
+ "banteng": 0,
538
+ "harimau": 0,
539
+ "gajah": 0,
540
+ "kambing": 0,
541
+ "panda": 0,
542
+ "buaya": 0,
543
+ "kerbau": 0,
544
+ "sapi": 0,
545
+ "monyet": 0,
546
+ "babihutan": 0,
547
+ "babi": 0,
548
+ "ayam": 0,
549
+ "apel": 20,
550
+ "ayamb": 0,
551
+ "ayamg": 0,
552
+ "ssapi": 0,
553
+ "sapir": 0,
554
+ "leleb": 0,
555
+ "leleg": 0,
556
+ "esteh": 0,
557
+ "pet": 0,
558
+ "potion": 0,
559
+ "sampah": 0,
560
+ "kucing": 0,
561
+ "kucinglastclaim": 0,
562
+ "kucingexp": 0,
563
+ "kuda": 0,
564
+ "kudalastclaim": 0,
565
+ "rubah": 0,
566
+ "rubahlastclaim": 0,
567
+ "rubahexp": 0,
568
+ "anjing": 0,
569
+ "anjinglastclaim": 0,
570
+ "anjingexp": 0,
571
+ "naga": 0,
572
+ "nagalastclaim": 0,
573
+ "griffin": 0,
574
+ "griffinlastclaim": 0,
575
+ "centaur": 0,
576
+ "fightnaga": 0,
577
+ "centaurlastclaim": 0,
578
+ "serigala": 0,
579
+ "serigalalastclaim": 0,
580
+ "serigalaexp": 0,
581
+ "phonix": 0,
582
+ "phonixlastclaim": 0,
583
+ "phonixexp": 0,
584
+ "makanannaga": 0,
585
+ "makananphonix": 0,
586
+ "makanancentaur": 0,
587
+ "makananserigala": 0,
588
+ "Banneduser": false,
589
+ "BannedReason": "",
590
+ "banned": false,
591
+ "bannedTime": 0,
592
+ "warn": 0,
593
+ "afk": -1,
594
+ "afkReason": "",
595
+ "anakkucing": 0,
596
+ "anakkuda": 0,
597
+ "anakrubah": 0,
598
+ "anakanjing": 0,
599
+ "makananpet": 0,
600
+ "makananPet": 0,
601
+ "antispam": 0,
602
+ "antispamlastclaim": 0,
603
+ "kayu": 0,
604
+ "batu": 0,
605
+ "string": 0,
606
+ "umpan": 0,
607
+ "armor": 0,
608
+ "armordurability": 0,
609
+ "weapon": 0,
610
+ "weapondurability": 0,
611
+ "sword": 0,
612
+ "sworddurability": 0,
613
+ "pickaxe": 0,
614
+ "pickaxedurability": 0,
615
+ "fishingrod": 0,
616
+ "fishingroddurability": 0,
617
+ "katana": 0,
618
+ "katanadurability": 0,
619
+ "bow": 0,
620
+ "bowdurability": 0,
621
+ "kapak": 0,
622
+ "kapakdurability": 0,
623
+ "axe": 0,
624
+ "axedurability": 0,
625
+ "pisau": 0,
626
+ "pisaudurability": 0,
627
+ "kerjasatu": 0,
628
+ "kerjadua": 0,
629
+ "kerjatiga": 0,
630
+ "kerjaempat": 0,
631
+ "kerjalima": 0,
632
+ "kerjaenam": 0,
633
+ "kerjatujuh": 0,
634
+ "kerjadelapan": 0,
635
+ "kerjasembilan": 0,
636
+ "kerjasepuluh": 0,
637
+ "kerjasebelas": 0,
638
+ "kerjaduabelas": 0,
639
+ "kerjatigabelas": 0,
640
+ "kerjaempatbelas": 0,
641
+ "kerjalimabelas": 0,
642
+ "pekerjaansatu": 0,
643
+ "pekerjaandua": 0,
644
+ "pekerjaantiga": 0,
645
+ "pekerjaanempat": 0,
646
+ "pekerjaanlima": 0,
647
+ "pekerjaanenam": 0,
648
+ "pekerjaantujuh": 0,
649
+ "pekerjaandelapan": 0,
650
+ "pekerjaansembilan": 0,
651
+ "pekerjaansepuluh": 0,
652
+ "pekerjaansebelas": 0,
653
+ "pekerjaanduabelas": 0,
654
+ "pekerjaantigabelas": 0,
655
+ "pekerjaanempatbelas": 0,
656
+ "pekerjaanlimabelas": 0,
657
+ "lastadventure": 0,
658
+ "lastwar": 0,
659
+ "lastberkebon": 0,
660
+ "lastberburu": 0,
661
+ "lastbansos": 0,
662
+ "lastrampok": 0,
663
+ "lastkill": 0,
664
+ "lastfishing": 0,
665
+ "lastdungeon": 0,
666
+ "lastduel": 0,
667
+ "lastmining": 0,
668
+ "lasthourly": 0,
669
+ "lastdagang": 0,
670
+ "lasthunt": 0,
671
+ "lasthun": 0,
672
+ "lastweekly": 0,
673
+ "lastmonthly": 0,
674
+ "lastyearly": 0,
675
+ "lastjb": 0,
676
+ "lastrob": 0,
677
+ "lastdaang": 0,
678
+ "lastngojek": 0,
679
+ "lastgrab": 0,
680
+ "lastngocok": 0,
681
+ "lastturu": 0,
682
+ "lastseen": 0,
683
+ "lastSetStatus": 0,
684
+ "registered": false,
685
+ "mangga": 0,
686
+ "stroberi": 0,
687
+ "semangka": 0,
688
+ "jeruk": 0,
689
+ "name": "irfan",
690
+ "age": -1,
691
+ "regTime": -1,
692
+ "premiumDate": -1,
693
+ "premium": false,
694
+ "premiumTime": 0,
695
+ "vip": "tidak",
696
+ "vipPoin": 0,
697
+ "job": "Pengangguran",
698
+ "jobexp": 0,
699
+ "jail": false,
700
+ "penjara": false,
701
+ "antarpaket": 0,
702
+ "dirawat": false,
703
+ "lbars": "[▒▒▒▒▒▒▒▒▒]",
704
+ "role": "Newbie ㋡",
705
+ "autolevelup": true,
706
+ "lastIstigfar": 0,
707
+ "skill": "",
708
+ "korps": "",
709
+ "korpsgrade": "",
710
+ "demon": "",
711
+ "breaths": "",
712
+ "magic": "",
713
+ "darahiblis": 0,
714
+ "demonblood": 0,
715
+ "demonkill": 0,
716
+ "hashirakill": 0,
717
+ "alldemonkill": 0,
718
+ "allhashirakill": 0,
719
+ "attack": 0,
720
+ "speed": 0,
721
+ "strenght": 0,
722
+ "defense": 0,
723
+ "regeneration": 0,
724
+ "ovo": 0,
725
+ "dana": 0,
726
+ "gopay": 0,
727
+ "lastngaji": 0,
728
+ "lastlonte": 0,
729
+ "lastkoboy": 0,
730
+ "lastdate": 0,
731
+ "lasttambang": 0,
732
+ "lastngepet": 0,
733
+ "glimit": 10,
734
+ "pertambangan": 0,
735
+ "lastbossbattle": 0,
736
+ "aqua": 0,
737
+ "glory": 0,
738
+ "enchant": 0,
739
+ "psepick": 0,
740
+ "psenjata": 0,
741
+ "lastgemclaim": 0,
742
+ "makanangriffin": 0,
743
+ "healthmonster": 0,
744
+ "anakserigala": 0,
745
+ "anaknaga": 0,
746
+ "anakphonix": 0,
747
+ "anakgriffin": 0,
748
+ "kyubi": 0,
749
+ "anakkyubi": 0,
750
+ "anakcentaur": 0,
751
+ "kingdom": false,
752
+ "lastsda": 0,
753
+ "lastberbru": 0,
754
+ "lastgift": 0,
755
+ "jualan": 0,
756
+ "lastjualan": 0,
757
+ "ngocokk": 0,
758
+ "lastngocokk": 0,
759
+ "lastcodereg": 0,
760
+ "anggur": 0,
761
+ "pisang": 0,
762
+ "bibitanggur": 0,
763
+ "bibitpisang": 0,
764
+ "bibitapel": 0,
765
+ "bibitmangga": 0,
766
+ "bibitjeruk": 0
767
+ },
768
+ "6281212181641@s.whatsapp.net": {
769
+ "taxi": 0,
770
+ "lasttaxi": 0,
771
+ "lastyoutuber": 0,
772
+ "subscribers": 0,
773
+ "viewers": 0,
774
+ "like": 0,
775
+ "playButton": 0,
776
+ "saldo": 0,
777
+ "pengeluaran": 0,
778
+ "healt": 100,
779
+ "health": 100,
780
+ "energi": 100,
781
+ "power": 100,
782
+ "title": 0,
783
+ "haus": 100,
784
+ "laper": 100,
785
+ "tprem": 0,
786
+ "stamina": 100,
787
+ "level": 0,
788
+ "follow": 0,
789
+ "lastfollow": 0,
790
+ "followers": 0,
791
+ "pasangan": "",
792
+ "sahabat": "",
793
+ "location": "Gubuk",
794
+ "titlein": "Belum Ada",
795
+ "ultah": "",
796
+ "waifu": "Belum Di Set",
797
+ "husbu": "Belum Di Set",
798
+ "pc": 0,
799
+ "exp": 13,
800
+ "coin": 0,
801
+ "atm": 0,
802
+ "limit": 100,
803
+ "skata": 0,
804
+ "tigame": 999,
805
+ "lastclaim": 0,
806
+ "judilast": 0,
807
+ "lastnambang": 0,
808
+ "lastnebang": 0,
809
+ "lastmulung": 0,
810
+ "lastkerja": 0,
811
+ "lastmaling": 0,
812
+ "lastbunuhi": 0,
813
+ "lastbisnis": 0,
814
+ "lastberbisnis": 0,
815
+ "bisnis": 0,
816
+ "berbisnis": 0,
817
+ "lastmancing": 0,
818
+ "pancing": 0,
819
+ "pancingan": 0,
820
+ "totalPancingan": 0,
821
+ "kardus": 0,
822
+ "botol": 0,
823
+ "kaleng": 0,
824
+ "money": 0,
825
+ "litecoin": 0,
826
+ "chip": 0,
827
+ "tiketcoin": 0,
828
+ "poin": 0,
829
+ "bank": 0,
830
+ "balance": 0,
831
+ "diamond": 0,
832
+ "emerald": 0,
833
+ "rock": 0,
834
+ "wood": 0,
835
+ "berlian": 0,
836
+ "iron": 0,
837
+ "emas": 0,
838
+ "common": 0,
839
+ "uncommon": 0,
840
+ "mythic": 0,
841
+ "legendary": 0,
842
+ "rumahsakit": 0,
843
+ "tambang": 0,
844
+ "camptroops": 0,
845
+ "pertanian": 0,
846
+ "fortress": 0,
847
+ "trofi": 0,
848
+ "rtrofi": "perunggu",
849
+ "makanan": 0,
850
+ "troopcamp": 0,
851
+ "shield": 0,
852
+ "arlok": 0,
853
+ "ojekk": 0,
854
+ "ojek": 0,
855
+ "lastngewe": 0,
856
+ "ngewe": 0,
857
+ "polisi": 0,
858
+ "pedagang": 0,
859
+ "dokter": 0,
860
+ "petani": 0,
861
+ "montir": 0,
862
+ "kuli": 0,
863
+ "korbanngocok": 0,
864
+ "coal": 0,
865
+ "korekapi": 0,
866
+ "ayambakar": 0,
867
+ "gulai": 0,
868
+ "rendang": 0,
869
+ "ayamgoreng": 0,
870
+ "oporayam": 0,
871
+ "steak": 0,
872
+ "babipanggang": 0,
873
+ "ikanbakar": 0,
874
+ "lelebakar": 0,
875
+ "nilabakar": 0,
876
+ "bawalbakar": 0,
877
+ "udangbakar": 0,
878
+ "pausbakar": 0,
879
+ "kepitingbakar": 0,
880
+ "soda": 0,
881
+ "vodka": 0,
882
+ "ganja": 0,
883
+ "bandage": 0,
884
+ "sushi": 0,
885
+ "roti": 0,
886
+ "ramuan": 0,
887
+ "lastramuanclaim": 0,
888
+ "gems": 0,
889
+ "cupon": 0,
890
+ "lastgemsclaim": 0,
891
+ "eleksirb": 0,
892
+ "penduduk": 0,
893
+ "archer": 0,
894
+ "shadow": 0,
895
+ "laststringclaim": 0,
896
+ "lastpotionclaim": 0,
897
+ "lastswordclaim": 0,
898
+ "lastweaponclaim": 0,
899
+ "lastironclaim": 0,
900
+ "lastmancingclaim": 0,
901
+ "anakpancingan": 0,
902
+ "as": 0,
903
+ "paus": 0,
904
+ "kepiting": 0,
905
+ "gurita": 0,
906
+ "cumi": 0,
907
+ "buntal": 0,
908
+ "dory": 0,
909
+ "lumba": 0,
910
+ "lobster": 0,
911
+ "hiu": 0,
912
+ "lele": 0,
913
+ "nila": 0,
914
+ "bawal": 0,
915
+ "udang": 0,
916
+ "ikan": 0,
917
+ "orca": 0,
918
+ "banteng": 0,
919
+ "harimau": 0,
920
+ "gajah": 0,
921
+ "kambing": 0,
922
+ "panda": 0,
923
+ "buaya": 0,
924
+ "kerbau": 0,
925
+ "sapi": 0,
926
+ "monyet": 0,
927
+ "babihutan": 0,
928
+ "babi": 0,
929
+ "ayam": 0,
930
+ "apel": 20,
931
+ "ayamb": 0,
932
+ "ayamg": 0,
933
+ "ssapi": 0,
934
+ "sapir": 0,
935
+ "leleb": 0,
936
+ "leleg": 0,
937
+ "esteh": 0,
938
+ "pet": 0,
939
+ "potion": 0,
940
+ "sampah": 0,
941
+ "kucing": 0,
942
+ "kucinglastclaim": 0,
943
+ "kucingexp": 0,
944
+ "kuda": 0,
945
+ "kudalastclaim": 0,
946
+ "rubah": 0,
947
+ "rubahlastclaim": 0,
948
+ "rubahexp": 0,
949
+ "anjing": 0,
950
+ "anjinglastclaim": 0,
951
+ "anjingexp": 0,
952
+ "naga": 0,
953
+ "nagalastclaim": 0,
954
+ "griffin": 0,
955
+ "griffinlastclaim": 0,
956
+ "centaur": 0,
957
+ "fightnaga": 0,
958
+ "centaurlastclaim": 0,
959
+ "serigala": 0,
960
+ "serigalalastclaim": 0,
961
+ "serigalaexp": 0,
962
+ "phonix": 0,
963
+ "phonixlastclaim": 0,
964
+ "phonixexp": 0,
965
+ "makanannaga": 0,
966
+ "makananphonix": 0,
967
+ "makanancentaur": 0,
968
+ "makananserigala": 0,
969
+ "Banneduser": false,
970
+ "BannedReason": "",
971
+ "banned": false,
972
+ "bannedTime": 0,
973
+ "warn": 0,
974
+ "afk": -1,
975
+ "afkReason": "",
976
+ "anakkucing": 0,
977
+ "anakkuda": 0,
978
+ "anakrubah": 0,
979
+ "anakanjing": 0,
980
+ "makananpet": 0,
981
+ "makananPet": 0,
982
+ "antispam": 0,
983
+ "antispamlastclaim": 0,
984
+ "kayu": 0,
985
+ "batu": 0,
986
+ "string": 0,
987
+ "umpan": 0,
988
+ "armor": 0,
989
+ "armordurability": 0,
990
+ "weapon": 0,
991
+ "weapondurability": 0,
992
+ "sword": 0,
993
+ "sworddurability": 0,
994
+ "pickaxe": 0,
995
+ "pickaxedurability": 0,
996
+ "fishingrod": 0,
997
+ "fishingroddurability": 0,
998
+ "katana": 0,
999
+ "katanadurability": 0,
1000
+ "bow": 0,
1001
+ "bowdurability": 0,
1002
+ "kapak": 0,
1003
+ "kapakdurability": 0,
1004
+ "axe": 0,
1005
+ "axedurability": 0,
1006
+ "pisau": 0,
1007
+ "pisaudurability": 0,
1008
+ "kerjasatu": 0,
1009
+ "kerjadua": 0,
1010
+ "kerjatiga": 0,
1011
+ "kerjaempat": 0,
1012
+ "kerjalima": 0,
1013
+ "kerjaenam": 0,
1014
+ "kerjatujuh": 0,
1015
+ "kerjadelapan": 0,
1016
+ "kerjasembilan": 0,
1017
+ "kerjasepuluh": 0,
1018
+ "kerjasebelas": 0,
1019
+ "kerjaduabelas": 0,
1020
+ "kerjatigabelas": 0,
1021
+ "kerjaempatbelas": 0,
1022
+ "kerjalimabelas": 0,
1023
+ "pekerjaansatu": 0,
1024
+ "pekerjaandua": 0,
1025
+ "pekerjaantiga": 0,
1026
+ "pekerjaanempat": 0,
1027
+ "pekerjaanlima": 0,
1028
+ "pekerjaanenam": 0,
1029
+ "pekerjaantujuh": 0,
1030
+ "pekerjaandelapan": 0,
1031
+ "pekerjaansembilan": 0,
1032
+ "pekerjaansepuluh": 0,
1033
+ "pekerjaansebelas": 0,
1034
+ "pekerjaanduabelas": 0,
1035
+ "pekerjaantigabelas": 0,
1036
+ "pekerjaanempatbelas": 0,
1037
+ "pekerjaanlimabelas": 0,
1038
+ "lastadventure": 0,
1039
+ "lastwar": 0,
1040
+ "lastberkebon": 0,
1041
+ "lastberburu": 0,
1042
+ "lastbansos": 0,
1043
+ "lastrampok": 0,
1044
+ "lastkill": 0,
1045
+ "lastfishing": 0,
1046
+ "lastdungeon": 0,
1047
+ "lastduel": 0,
1048
+ "lastmining": 0,
1049
+ "lasthourly": 0,
1050
+ "lastdagang": 0,
1051
+ "lasthunt": 0,
1052
+ "lasthun": 0,
1053
+ "lastweekly": 0,
1054
+ "lastmonthly": 0,
1055
+ "lastyearly": 0,
1056
+ "lastjb": 0,
1057
+ "lastrob": 0,
1058
+ "lastdaang": 0,
1059
+ "lastngojek": 0,
1060
+ "lastgrab": 0,
1061
+ "lastngocok": 0,
1062
+ "lastturu": 0,
1063
+ "lastseen": 0,
1064
+ "lastSetStatus": 0,
1065
+ "registered": false,
1066
+ "mangga": 0,
1067
+ "stroberi": 0,
1068
+ "semangka": 0,
1069
+ "jeruk": 0,
1070
+ "name": "IKYBOT AUTOAI",
1071
+ "age": -1,
1072
+ "regTime": -1,
1073
+ "premiumDate": -1,
1074
+ "premium": false,
1075
+ "premiumTime": 0,
1076
+ "vip": "tidak",
1077
+ "vipPoin": 0,
1078
+ "job": "Pengangguran",
1079
+ "jobexp": 0,
1080
+ "jail": false,
1081
+ "penjara": false,
1082
+ "antarpaket": 0,
1083
+ "dirawat": false,
1084
+ "lbars": "[▒▒▒▒▒▒▒▒▒]",
1085
+ "role": "Newbie ㋡",
1086
+ "autolevelup": true,
1087
+ "lastIstigfar": 0,
1088
+ "skill": "",
1089
+ "korps": "",
1090
+ "korpsgrade": "",
1091
+ "demon": "",
1092
+ "breaths": "",
1093
+ "magic": "",
1094
+ "darahiblis": 0,
1095
+ "demonblood": 0,
1096
+ "demonkill": 0,
1097
+ "hashirakill": 0,
1098
+ "alldemonkill": 0,
1099
+ "allhashirakill": 0,
1100
+ "attack": 0,
1101
+ "speed": 0,
1102
+ "strenght": 0,
1103
+ "defense": 0,
1104
+ "regeneration": 0,
1105
+ "ovo": 0,
1106
+ "dana": 0,
1107
+ "gopay": 0,
1108
+ "lastngaji": 0,
1109
+ "lastlonte": 0,
1110
+ "lastkoboy": 0,
1111
+ "lastdate": 0,
1112
+ "lasttambang": 0,
1113
+ "lastngepet": 0,
1114
+ "glimit": 10,
1115
+ "pertambangan": 0,
1116
+ "lastbossbattle": 0,
1117
+ "aqua": 0,
1118
+ "glory": 0,
1119
+ "enchant": 0,
1120
+ "psepick": 0,
1121
+ "psenjata": 0,
1122
+ "lastgemclaim": 0,
1123
+ "makanangriffin": 0,
1124
+ "healthmonster": 0,
1125
+ "anakserigala": 0,
1126
+ "anaknaga": 0,
1127
+ "anakphonix": 0,
1128
+ "anakgriffin": 0,
1129
+ "kyubi": 0,
1130
+ "anakkyubi": 0,
1131
+ "anakcentaur": 0,
1132
+ "kingdom": false,
1133
+ "lastsda": 0,
1134
+ "lastberbru": 0,
1135
+ "lastgift": 0,
1136
+ "jualan": 0,
1137
+ "lastjualan": 0,
1138
+ "ngocokk": 0,
1139
+ "lastngocokk": 0,
1140
+ "lastcodereg": 0,
1141
+ "anggur": 0,
1142
+ "pisang": 0,
1143
+ "bibitanggur": 0,
1144
+ "bibitpisang": 0,
1145
+ "bibitapel": 0,
1146
+ "bibitmangga": 0,
1147
+ "bibitjeruk": 0
1148
+ },
1149
+ "6287821561429@s.whatsapp.net": {
1150
+ "taxi": 0,
1151
+ "lasttaxi": 0,
1152
+ "lastyoutuber": 0,
1153
+ "subscribers": 0,
1154
+ "viewers": 0,
1155
+ "like": 0,
1156
+ "playButton": 0,
1157
+ "saldo": 0,
1158
+ "pengeluaran": 0,
1159
+ "healt": 100,
1160
+ "health": 100,
1161
+ "energi": 100,
1162
+ "power": 100,
1163
+ "title": 0,
1164
+ "haus": 100,
1165
+ "laper": 100,
1166
+ "tprem": 0,
1167
+ "stamina": 100,
1168
+ "level": 0,
1169
+ "follow": 0,
1170
+ "lastfollow": 0,
1171
+ "followers": 0,
1172
+ "pasangan": "",
1173
+ "sahabat": "",
1174
+ "location": "Gubuk",
1175
+ "titlein": "Belum Ada",
1176
+ "ultah": "",
1177
+ "waifu": "Belum Di Set",
1178
+ "husbu": "Belum Di Set",
1179
+ "pc": 0,
1180
+ "exp": 18,
1181
+ "coin": 0,
1182
+ "atm": 0,
1183
+ "limit": 100,
1184
+ "skata": 0,
1185
+ "tigame": 999,
1186
+ "lastclaim": 0,
1187
+ "judilast": 0,
1188
+ "lastnambang": 0,
1189
+ "lastnebang": 0,
1190
+ "lastmulung": 0,
1191
+ "lastkerja": 0,
1192
+ "lastmaling": 0,
1193
+ "lastbunuhi": 0,
1194
+ "lastbisnis": 0,
1195
+ "lastberbisnis": 0,
1196
+ "bisnis": 0,
1197
+ "berbisnis": 0,
1198
+ "lastmancing": 0,
1199
+ "pancing": 0,
1200
+ "pancingan": 0,
1201
+ "totalPancingan": 0,
1202
+ "kardus": 0,
1203
+ "botol": 0,
1204
+ "kaleng": 0,
1205
+ "money": 0,
1206
+ "litecoin": 0,
1207
+ "chip": 0,
1208
+ "tiketcoin": 0,
1209
+ "poin": 0,
1210
+ "bank": 0,
1211
+ "balance": 0,
1212
+ "diamond": 0,
1213
+ "emerald": 0,
1214
+ "rock": 0,
1215
+ "wood": 0,
1216
+ "berlian": 0,
1217
+ "iron": 0,
1218
+ "emas": 0,
1219
+ "common": 0,
1220
+ "uncommon": 0,
1221
+ "mythic": 0,
1222
+ "legendary": 0,
1223
+ "rumahsakit": 0,
1224
+ "tambang": 0,
1225
+ "camptroops": 0,
1226
+ "pertanian": 0,
1227
+ "fortress": 0,
1228
+ "trofi": 0,
1229
+ "rtrofi": "perunggu",
1230
+ "makanan": 0,
1231
+ "troopcamp": 0,
1232
+ "shield": 0,
1233
+ "arlok": 0,
1234
+ "ojekk": 0,
1235
+ "ojek": 0,
1236
+ "lastngewe": 0,
1237
+ "ngewe": 0,
1238
+ "polisi": 0,
1239
+ "pedagang": 0,
1240
+ "dokter": 0,
1241
+ "petani": 0,
1242
+ "montir": 0,
1243
+ "kuli": 0,
1244
+ "korbanngocok": 0,
1245
+ "coal": 0,
1246
+ "korekapi": 0,
1247
+ "ayambakar": 0,
1248
+ "gulai": 0,
1249
+ "rendang": 0,
1250
+ "ayamgoreng": 0,
1251
+ "oporayam": 0,
1252
+ "steak": 0,
1253
+ "babipanggang": 0,
1254
+ "ikanbakar": 0,
1255
+ "lelebakar": 0,
1256
+ "nilabakar": 0,
1257
+ "bawalbakar": 0,
1258
+ "udangbakar": 0,
1259
+ "pausbakar": 0,
1260
+ "kepitingbakar": 0,
1261
+ "soda": 0,
1262
+ "vodka": 0,
1263
+ "ganja": 0,
1264
+ "bandage": 0,
1265
+ "sushi": 0,
1266
+ "roti": 0,
1267
+ "ramuan": 0,
1268
+ "lastramuanclaim": 0,
1269
+ "gems": 0,
1270
+ "cupon": 0,
1271
+ "lastgemsclaim": 0,
1272
+ "eleksirb": 0,
1273
+ "penduduk": 0,
1274
+ "archer": 0,
1275
+ "shadow": 0,
1276
+ "laststringclaim": 0,
1277
+ "lastpotionclaim": 0,
1278
+ "lastswordclaim": 0,
1279
+ "lastweaponclaim": 0,
1280
+ "lastironclaim": 0,
1281
+ "lastmancingclaim": 0,
1282
+ "anakpancingan": 0,
1283
+ "as": 0,
1284
+ "paus": 0,
1285
+ "kepiting": 0,
1286
+ "gurita": 0,
1287
+ "cumi": 0,
1288
+ "buntal": 0,
1289
+ "dory": 0,
1290
+ "lumba": 0,
1291
+ "lobster": 0,
1292
+ "hiu": 0,
1293
+ "lele": 0,
1294
+ "nila": 0,
1295
+ "bawal": 0,
1296
+ "udang": 0,
1297
+ "ikan": 0,
1298
+ "orca": 0,
1299
+ "banteng": 0,
1300
+ "harimau": 0,
1301
+ "gajah": 0,
1302
+ "kambing": 0,
1303
+ "panda": 0,
1304
+ "buaya": 0,
1305
+ "kerbau": 0,
1306
+ "sapi": 0,
1307
+ "monyet": 0,
1308
+ "babihutan": 0,
1309
+ "babi": 0,
1310
+ "ayam": 0,
1311
+ "apel": 20,
1312
+ "ayamb": 0,
1313
+ "ayamg": 0,
1314
+ "ssapi": 0,
1315
+ "sapir": 0,
1316
+ "leleb": 0,
1317
+ "leleg": 0,
1318
+ "esteh": 0,
1319
+ "pet": 0,
1320
+ "potion": 0,
1321
+ "sampah": 0,
1322
+ "kucing": 0,
1323
+ "kucinglastclaim": 0,
1324
+ "kucingexp": 0,
1325
+ "kuda": 0,
1326
+ "kudalastclaim": 0,
1327
+ "rubah": 0,
1328
+ "rubahlastclaim": 0,
1329
+ "rubahexp": 0,
1330
+ "anjing": 0,
1331
+ "anjinglastclaim": 0,
1332
+ "anjingexp": 0,
1333
+ "naga": 0,
1334
+ "nagalastclaim": 0,
1335
+ "griffin": 0,
1336
+ "griffinlastclaim": 0,
1337
+ "centaur": 0,
1338
+ "fightnaga": 0,
1339
+ "centaurlastclaim": 0,
1340
+ "serigala": 0,
1341
+ "serigalalastclaim": 0,
1342
+ "serigalaexp": 0,
1343
+ "phonix": 0,
1344
+ "phonixlastclaim": 0,
1345
+ "phonixexp": 0,
1346
+ "makanannaga": 0,
1347
+ "makananphonix": 0,
1348
+ "makanancentaur": 0,
1349
+ "makananserigala": 0,
1350
+ "Banneduser": false,
1351
+ "BannedReason": "",
1352
+ "banned": false,
1353
+ "bannedTime": 0,
1354
+ "warn": 0,
1355
+ "afk": -1,
1356
+ "afkReason": "",
1357
+ "anakkucing": 0,
1358
+ "anakkuda": 0,
1359
+ "anakrubah": 0,
1360
+ "anakanjing": 0,
1361
+ "makananpet": 0,
1362
+ "makananPet": 0,
1363
+ "antispam": 0,
1364
+ "antispamlastclaim": 0,
1365
+ "kayu": 0,
1366
+ "batu": 0,
1367
+ "string": 0,
1368
+ "umpan": 0,
1369
+ "armor": 0,
1370
+ "armordurability": 0,
1371
+ "weapon": 0,
1372
+ "weapondurability": 0,
1373
+ "sword": 0,
1374
+ "sworddurability": 0,
1375
+ "pickaxe": 0,
1376
+ "pickaxedurability": 0,
1377
+ "fishingrod": 0,
1378
+ "fishingroddurability": 0,
1379
+ "katana": 0,
1380
+ "katanadurability": 0,
1381
+ "bow": 0,
1382
+ "bowdurability": 0,
1383
+ "kapak": 0,
1384
+ "kapakdurability": 0,
1385
+ "axe": 0,
1386
+ "axedurability": 0,
1387
+ "pisau": 0,
1388
+ "pisaudurability": 0,
1389
+ "kerjasatu": 0,
1390
+ "kerjadua": 0,
1391
+ "kerjatiga": 0,
1392
+ "kerjaempat": 0,
1393
+ "kerjalima": 0,
1394
+ "kerjaenam": 0,
1395
+ "kerjatujuh": 0,
1396
+ "kerjadelapan": 0,
1397
+ "kerjasembilan": 0,
1398
+ "kerjasepuluh": 0,
1399
+ "kerjasebelas": 0,
1400
+ "kerjaduabelas": 0,
1401
+ "kerjatigabelas": 0,
1402
+ "kerjaempatbelas": 0,
1403
+ "kerjalimabelas": 0,
1404
+ "pekerjaansatu": 0,
1405
+ "pekerjaandua": 0,
1406
+ "pekerjaantiga": 0,
1407
+ "pekerjaanempat": 0,
1408
+ "pekerjaanlima": 0,
1409
+ "pekerjaanenam": 0,
1410
+ "pekerjaantujuh": 0,
1411
+ "pekerjaandelapan": 0,
1412
+ "pekerjaansembilan": 0,
1413
+ "pekerjaansepuluh": 0,
1414
+ "pekerjaansebelas": 0,
1415
+ "pekerjaanduabelas": 0,
1416
+ "pekerjaantigabelas": 0,
1417
+ "pekerjaanempatbelas": 0,
1418
+ "pekerjaanlimabelas": 0,
1419
+ "lastadventure": 0,
1420
+ "lastwar": 0,
1421
+ "lastberkebon": 0,
1422
+ "lastberburu": 0,
1423
+ "lastbansos": 0,
1424
+ "lastrampok": 0,
1425
+ "lastkill": 0,
1426
+ "lastfishing": 0,
1427
+ "lastdungeon": 0,
1428
+ "lastduel": 0,
1429
+ "lastmining": 0,
1430
+ "lasthourly": 0,
1431
+ "lastdagang": 0,
1432
+ "lasthunt": 0,
1433
+ "lasthun": 0,
1434
+ "lastweekly": 0,
1435
+ "lastmonthly": 0,
1436
+ "lastyearly": 0,
1437
+ "lastjb": 0,
1438
+ "lastrob": 0,
1439
+ "lastdaang": 0,
1440
+ "lastngojek": 0,
1441
+ "lastgrab": 0,
1442
+ "lastngocok": 0,
1443
+ "lastturu": 0,
1444
+ "lastseen": 0,
1445
+ "lastSetStatus": 0,
1446
+ "registered": false,
1447
+ "mangga": 0,
1448
+ "stroberi": 0,
1449
+ "semangka": 0,
1450
+ "jeruk": 0,
1451
+ "name": "+62 878-2156-1429",
1452
+ "age": -1,
1453
+ "regTime": -1,
1454
+ "premiumDate": -1,
1455
+ "premium": false,
1456
+ "premiumTime": 0,
1457
+ "vip": "tidak",
1458
+ "vipPoin": 0,
1459
+ "job": "Pengangguran",
1460
+ "jobexp": 0,
1461
+ "jail": false,
1462
+ "penjara": false,
1463
+ "antarpaket": 0,
1464
+ "dirawat": false,
1465
+ "lbars": "[▒▒▒▒▒▒▒▒▒]",
1466
+ "role": "Newbie ㋡",
1467
+ "autolevelup": true,
1468
+ "lastIstigfar": 0,
1469
+ "skill": "",
1470
+ "korps": "",
1471
+ "korpsgrade": "",
1472
+ "demon": "",
1473
+ "breaths": "",
1474
+ "magic": "",
1475
+ "darahiblis": 0,
1476
+ "demonblood": 0,
1477
+ "demonkill": 0,
1478
+ "hashirakill": 0,
1479
+ "alldemonkill": 0,
1480
+ "allhashirakill": 0,
1481
+ "attack": 0,
1482
+ "speed": 0,
1483
+ "strenght": 0,
1484
+ "defense": 0,
1485
+ "regeneration": 0,
1486
+ "ovo": 0,
1487
+ "dana": 0,
1488
+ "gopay": 0,
1489
+ "lastngaji": 0,
1490
+ "lastlonte": 0,
1491
+ "lastkoboy": 0,
1492
+ "lastdate": 0,
1493
+ "lasttambang": 0,
1494
+ "lastngepet": 0,
1495
+ "glimit": 10,
1496
+ "pertambangan": 0,
1497
+ "lastbossbattle": 0,
1498
+ "aqua": 0,
1499
+ "glory": 0,
1500
+ "enchant": 0,
1501
+ "psepick": 0,
1502
+ "psenjata": 0,
1503
+ "lastgemclaim": 0,
1504
+ "makanangriffin": 0,
1505
+ "healthmonster": 0,
1506
+ "anakserigala": 0,
1507
+ "anaknaga": 0,
1508
+ "anakphonix": 0,
1509
+ "anakgriffin": 0,
1510
+ "kyubi": 0,
1511
+ "anakkyubi": 0,
1512
+ "anakcentaur": 0,
1513
+ "kingdom": false,
1514
+ "lastsda": 0,
1515
+ "lastberbru": 0,
1516
+ "lastgift": 0,
1517
+ "jualan": 0,
1518
+ "lastjualan": 0,
1519
+ "ngocokk": 0,
1520
+ "lastngocokk": 0,
1521
+ "lastcodereg": 0,
1522
+ "anggur": 0,
1523
+ "pisang": 0,
1524
+ "bibitanggur": 0,
1525
+ "bibitpisang": 0,
1526
+ "bibitapel": 0,
1527
+ "bibitmangga": 0,
1528
+ "bibitjeruk": 0
1529
+ }
1530
+ },
1531
+ "chats": {
1532
+ "6285878836361@s.whatsapp.net": {
1533
+ "isBanned": false,
1534
+ "welcome": true,
1535
+ "welcometype": 1,
1536
+ "detect": false,
1537
+ "isBannedTime": false,
1538
+ "mute": false,
1539
+ "listStr": {},
1540
+ "sWelcome": "Hai, @user!\nSelamat datang di grup @subject\n\n@desc",
1541
+ "sBye": "Selamat tinggal @user!",
1542
+ "sPromote": "",
1543
+ "sDemote": "",
1544
+ "delete": false,
1545
+ "antiLink": false,
1546
+ "antiLinknokick": false,
1547
+ "antiSticker": false,
1548
+ "antiStickernokick": false,
1549
+ "viewonce": false,
1550
+ "antiToxic": true,
1551
+ "antilinkig": false,
1552
+ "antilinkignokick": false,
1553
+ "antilinkyt": false,
1554
+ "antilinkytnokick": false,
1555
+ "antilinktwit": false,
1556
+ "antilinktwitnokick": false,
1557
+ "antilinkfb": false,
1558
+ "antilinkfbnokick": false,
1559
+ "antilinkall": false,
1560
+ "antilinkallnokick": false,
1561
+ "antilinkwame": false,
1562
+ "antilinkwamenokick": false,
1563
+ "antilinktele": false,
1564
+ "antilinktelenokick": false,
1565
+ "antilinktt": false,
1566
+ "antilinkttnokick": false,
1567
+ "antibot": false,
1568
+ "rpg": false,
1569
+ "expired": 0,
1570
+ "memgc": {
1571
+ "6285878836361@s.whatsapp.net": {
1572
+ "blacklist": false,
1573
+ "banned": false,
1574
+ "bannedTime": 0,
1575
+ "chat": 0,
1576
+ "chatTotal": 0,
1577
+ "command": 0,
1578
+ "commandTotal": 0,
1579
+ "lastseen": 0
1580
+ },
1581
+ "6283121935164@s.whatsapp.net": {
1582
+ "blacklist": false,
1583
+ "banned": false,
1584
+ "bannedTime": 0,
1585
+ "chat": 0,
1586
+ "chatTotal": 0,
1587
+ "command": 0,
1588
+ "commandTotal": 0,
1589
+ "lastseen": 0
1590
+ },
1591
+ "6287821561429@s.whatsapp.net": {
1592
+ "blacklist": false,
1593
+ "banned": false,
1594
+ "bannedTime": 0,
1595
+ "chat": 0,
1596
+ "chatTotal": 0,
1597
+ "command": 0,
1598
+ "commandTotal": 0,
1599
+ "lastseen": 0
1600
+ }
1601
+ }
1602
+ },
1603
+ "6281212181641@s.whatsapp.net": {
1604
+ "isBanned": false,
1605
+ "welcome": true,
1606
+ "welcometype": 1,
1607
+ "detect": false,
1608
+ "isBannedTime": false,
1609
+ "mute": false,
1610
+ "listStr": {},
1611
+ "sWelcome": "Hai, @user!\nSelamat datang di grup @subject\n\n@desc",
1612
+ "sBye": "Selamat tinggal @user!",
1613
+ "sPromote": "",
1614
+ "sDemote": "",
1615
+ "delete": false,
1616
+ "antiLink": false,
1617
+ "antiLinknokick": false,
1618
+ "antiSticker": false,
1619
+ "antiStickernokick": false,
1620
+ "viewonce": false,
1621
+ "antiToxic": true,
1622
+ "antilinkig": false,
1623
+ "antilinkignokick": false,
1624
+ "antilinkyt": false,
1625
+ "antilinkytnokick": false,
1626
+ "antilinktwit": false,
1627
+ "antilinktwitnokick": false,
1628
+ "antilinkfb": false,
1629
+ "antilinkfbnokick": false,
1630
+ "antilinkall": false,
1631
+ "antilinkallnokick": false,
1632
+ "antilinkwame": false,
1633
+ "antilinkwamenokick": false,
1634
+ "antilinktele": false,
1635
+ "antilinktelenokick": false,
1636
+ "antilinktt": false,
1637
+ "antilinkttnokick": false,
1638
+ "antibot": false,
1639
+ "rpg": false,
1640
+ "expired": 0,
1641
+ "memgc": {
1642
+ "6281212181641@s.whatsapp.net": {
1643
+ "blacklist": false,
1644
+ "banned": false,
1645
+ "bannedTime": 0,
1646
+ "chat": 0,
1647
+ "chatTotal": 0,
1648
+ "command": 0,
1649
+ "commandTotal": 0,
1650
+ "lastseen": 0
1651
+ }
1652
+ }
1653
+ },
1654
+ "6287821561429@s.whatsapp.net": {
1655
+ "isBanned": false,
1656
+ "welcome": true,
1657
+ "welcometype": 1,
1658
+ "detect": false,
1659
+ "isBannedTime": false,
1660
+ "mute": false,
1661
+ "listStr": {},
1662
+ "sWelcome": "Hai, @user!\nSelamat datang di grup @subject\n\n@desc",
1663
+ "sBye": "Selamat tinggal @user!",
1664
+ "sPromote": "",
1665
+ "sDemote": "",
1666
+ "delete": false,
1667
+ "antiLink": false,
1668
+ "antiLinknokick": false,
1669
+ "antiSticker": false,
1670
+ "antiStickernokick": false,
1671
+ "viewonce": false,
1672
+ "antiToxic": true,
1673
+ "antilinkig": false,
1674
+ "antilinkignokick": false,
1675
+ "antilinkyt": false,
1676
+ "antilinkytnokick": false,
1677
+ "antilinktwit": false,
1678
+ "antilinktwitnokick": false,
1679
+ "antilinkfb": false,
1680
+ "antilinkfbnokick": false,
1681
+ "antilinkall": false,
1682
+ "antilinkallnokick": false,
1683
+ "antilinkwame": false,
1684
+ "antilinkwamenokick": false,
1685
+ "antilinktele": false,
1686
+ "antilinktelenokick": false,
1687
+ "antilinktt": false,
1688
+ "antilinkttnokick": false,
1689
+ "antibot": false,
1690
+ "rpg": false,
1691
+ "expired": 0,
1692
+ "memgc": {
1693
+ "6287821561429@s.whatsapp.net": {
1694
+ "blacklist": false,
1695
+ "banned": false,
1696
+ "bannedTime": 0,
1697
+ "chat": 0,
1698
+ "chatTotal": 0,
1699
+ "command": 0,
1700
+ "commandTotal": 0,
1701
+ "lastseen": 0
1702
+ }
1703
+ }
1704
+ }
1705
+ },
1706
+ "stats": {
1707
+ "menu.js": {
1708
+ "total": 2,
1709
+ "success": 2,
1710
+ "last": 1732074269621,
1711
+ "lastSuccess": 1732074269621
1712
+ },
1713
+ "downloader-pindl.js": {
1714
+ "total": 2,
1715
+ "success": 0,
1716
+ "last": 1732074298135,
1717
+ "lastSuccess": 0
1718
+ },
1719
+ "downloader-pinterest.js": {
1720
+ "total": 2,
1721
+ "success": 2,
1722
+ "last": 1732074374075,
1723
+ "lastSuccess": 1732074374075
1724
+ },
1725
+ "server.js": {
1726
+ "total": 3,
1727
+ "success": 3,
1728
+ "last": 1733916896776,
1729
+ "lastSuccess": 1733916896776
1730
+ }
1731
+ },
1732
+ "msgs": {},
1733
+ "sticker": {}
1734
+ }
docker-compose.yml ADDED
@@ -0,0 +1,15 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ version: "3.9"
2
+ services:
3
+ web:
4
+ build: .
5
+ ports:
6
+ - "8000:5000"
7
+ volumes:
8
+ - .:/code
9
+ - logvolume01:/var/log
10
+ links:
11
+ - redis
12
+ redis:
13
+ image: redis
14
+ volumes:
15
+ logvolume01: {}
handler.js ADDED
@@ -0,0 +1,1261 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const simple = require('./lib/simple')
2
+ const util = require('util')
3
+
4
+ const isNumber = x => typeof x === 'number' && !isNaN(x)
5
+ const delay = ms => isNumber(ms) && new Promise(resolve => setTimeout(resolve, ms))
6
+
7
+ module.exports = {
8
+ async handler(chatUpdate) {
9
+ if (global.db.data == null) await loadDatabase()
10
+ this.msgqueque = this.msgqueque || []
11
+ // console.log(chatUpdate)
12
+ if (!chatUpdate) return
13
+ // if (chatUpdate.messages.length > 2 || !chatUpdate.messages.length) return
14
+ if (chatUpdate.messages.length > 1) console.log(chatUpdate.messages)
15
+ let m = chatUpdate.messages[chatUpdate.messages.length - 1]
16
+ if (!m) return
17
+ //console.log(JSON.stringify(m, null, 4))
18
+ try {
19
+ m = simple.smsg(this, m) || m
20
+ if (!m) return
21
+ // console.log(m)
22
+ m.exp = 0
23
+ m.limit = false
24
+ try {
25
+ let user = global.db.data.users[m.sender]
26
+ if (typeof user !== 'object') global.db.data.users[m.sender] = {}
27
+ if (user) {
28
+ if (!isNumber(user.saldo)) user.saldo = 0
29
+ if (!isNumber(user.pengeluaran)) user.pengeluaran = 0
30
+ if (!isNumber(user.healt)) user.healt = 100
31
+ if (!isNumber(user.health)) user.health = 100
32
+ if (!isNumber(user.energi)) user.energi = 100
33
+ if (!isNumber(user.power)) user.power = 100
34
+ if (!isNumber(user.title)) user.title = 0
35
+ if (!isNumber(user.stamina)) user.stamina = 100
36
+ if (!isNumber(user.haus)) user.haus = 100
37
+ if (!isNumber(user.laper)) user.laper = 100
38
+ if (!isNumber(user.level)) user.level = 0
39
+ if (!('titlein' in user)) user.titlein = 'Belum Ada'
40
+ if (!("ultah" in user)) user.ultah = ''
41
+ if (!('pasangan' in user)) user.pasangan = ''
42
+ if (!('sahabat' in user)) user.sahabat = ''
43
+ if (!('location' in user)) user.location = 'Gubuk'
44
+ if (!('husbu' in user)) user.husbu = 'Belum Di Set'
45
+ if (!('waifu' in user)) user.waifu = 'Belum Di Set'
46
+ if (!isNumber(user.follow)) user.follow = 0
47
+ if (!isNumber(user.lastfollow)) user.lastfollow = 0
48
+ if (!isNumber(user.followers)) user.followers = 0
49
+ if (!isNumber(user.exp)) user.exp = 0
50
+ if (!isNumber(user.pc)) user.pc = 0
51
+ if (!isNumber(user.korbanngocok)) user.korbanngocok = 0
52
+ if (!isNumber(user.ojekk)) user.ojekk = 0
53
+ if (!isNumber(user.polisi)) user.polisi = 0
54
+ if (!isNumber(user.ojek)) user.ojek = 0
55
+ if (!isNumber(user.pedagang)) user.pedagang = 0
56
+ if (!isNumber(user.dokter)) user.dokter = 0
57
+ if (!isNumber(user.petani)) user.petani = 0
58
+ if (!isNumber(user.montir)) user.montir = 0
59
+ if (!isNumber(user.kuli)) user.kuli = 0
60
+ if (!isNumber(user.trofi)) user.trofi= 0
61
+ if (!user.rtrofi) user.rtrofi = 'Perunggu'
62
+ if (!isNumber(user.troopcamp)) user.troopcamp = 0
63
+ if (!isNumber(user.coin)) user.coin = 0
64
+ if (!isNumber(user.atm)) user.atm = 0
65
+ if (!isNumber(user.limit)) user.limit = 100
66
+ if (!isNumber(user.glimit)) user.glimit = 10
67
+ if (!isNumber(user.tprem)) user.tprem = 0
68
+ if (!isNumber(user.tigame)) user.tigame = 5
69
+ if (!isNumber(user.lastclaim)) user.lastclaim = 0
70
+ if (isNumber(user.lastmulung)) user.lastmulung = 0
71
+ if (!isNumber(user.judilast)) user.judilast = 0
72
+ if (!isNumber(user.lastnambang)) user.lastnambang = 0
73
+ if (!isNumber(user.lastnebang)) user.lastnebang = 0
74
+ if (!isNumber(user.lastkerja)) user.lastkerja = 0
75
+ if (!isNumber(user.lastmaling)) user.lastmaling = 0
76
+ if (!isNumber(user.lastbunuhi)) user.lastbunuhi = 0
77
+ if (!isNumber(user.lastbisnis)) user.lastbisnis = 0
78
+ if (!isNumber(user.lastberbisnis)) user.lastberbisnis = 0
79
+ if (!isNumber(user.berbisnis)) user.berbisnis = 0
80
+ if (!isNumber(user.bisnis)) user.bisnis = 0
81
+ if (!isNumber(user.lastmancing)) user.lastmancing = 0
82
+ if (!isNumber(user.money)) user.money = 0
83
+ if (!isNumber(user.rumahsakit)) user.rumahsakit= 0
84
+ if (!isNumber(user.fortress)) user.fortress = 0
85
+ if (!isNumber(user.shield)) user.shield = false
86
+ if (!isNumber(user.pertanian)) user.pertanian = 0
87
+ if (!isNumber(user.pertambangan)) user.pertambangan = 0
88
+ if (!isNumber(user.camptroops)) user.camptroops = 0
89
+ if (!isNumber(user.tambang)) user.tambang = 0
90
+
91
+ //Tambahan rpg
92
+ if (!isNumber(user.litecoin)) user.litecoin = 0
93
+ if (!isNumber(user.chip)) user.chip = 0
94
+ if (!isNumber(user.tiketcoin)) user.tiketcoin = 0
95
+ if (!isNumber(user.poin)) user.poin = 0
96
+ if (!isNumber (user.lastbossbattle)) user.lastbossbattle = 0
97
+ if (!isNumber (user.bank)) user.bank = 0
98
+ if (!isNumber (user.balance)) user.balance = 0
99
+
100
+ if (!isNumber(user.botol)) user.botol = 0
101
+ if (!isNumber(user.kardus)) user.kardus = 0
102
+ if (!isNumber(user.kaleng)) user.kaleng = 0
103
+ if (!isNumber(user.aqua)) user.aqua = 0
104
+ if (!isNumber(user.diamond)) user.diamond = 0
105
+ if (!isNumber(user.emerald)) user.emerald = 0
106
+ if (!isNumber(user.wood)) user.wood = 0
107
+ if (!isNumber(user.rock)) user.rock = 0
108
+ if (!isNumber(user.berlian)) user.berlian = 0
109
+ if (!isNumber(user.iron)) user.iron = 0
110
+ if (!isNumber(user.emas)) user.emas = 0
111
+ if (!isNumber(user.arlok)) user.arlok = 0
112
+
113
+ if (!isNumber(user.common)) user.common = 0
114
+ if (!isNumber(user.as)) user.as = 0
115
+ if (!isNumber(user.uncommon)) user.uncommon = 0
116
+ if (!isNumber(user.mythic)) user.mythic = 0
117
+ if (!isNumber(user.legendary)) user.legendary = 0
118
+ if (!isNumber(user.glory)) user.glory = 0
119
+ if (!isNumber(user.enchant)) user.enchant = 0
120
+ if (!isNumber(user.pet)) user.pet = 0
121
+ if (!isNumber(user.psepick)) user.psepick = 0
122
+ if (!isNumber(user.psenjata)) user.psenjata = 0
123
+ //rpg meracik
124
+ if (!isNumber(user.lastramuanclaim)) user.lastramuanclaim = 0
125
+ if (!isNumber(user.gems)) user.gems = 0
126
+ if (!isNumber(user.cupon)) user.cupon = 0
127
+ if (!isNumber(user.lastgemclaim)) user.lastgemclaim = 0
128
+ if (!isNumber(user.eleksirb)) user.eleksirb = 0
129
+ if (!isNumber(user.penduduk)) user.penduduk = 0
130
+ if (!isNumber(user.archer)) user.archer = 0
131
+ if (!isNumber(user.shadow)) user.shadow = 0
132
+ if (!isNumber(user.lastpotionclaim)) user.lastpotionclaim = 0
133
+ if (!isNumber(user.laststringclaim)) user.laststringclaim = 0
134
+ if (!isNumber(user.lastswordclaim)) user.lastswordclaim = 0
135
+ if (!isNumber(user.lastweaponclaim)) user.lastweaponclaim = 0
136
+ if (!isNumber(user.lastironclaim)) user.lastironclaim = 0
137
+ if (!isNumber(user.lastmancingclaim)) user.lastmancingclaim = 0
138
+ if (!isNumber(user.anakpancingan)) user.anakpancingan = 0
139
+
140
+ if (!isNumber(user.potion)) user.potion = 0
141
+ if (!isNumber(user.sampah)) user.sampah = 0
142
+ if (!isNumber(user.pancing)) user.pancing = 0
143
+ if (!isNumber(user.pancingan)) user.pancingan = 0
144
+ if (!isNumber(user.totalPancingan)) user.totalPancingan = 0
145
+ //penambah stamina
146
+ if (!isNumber(user.apel)) user.apel = 0
147
+ if (!isNumber(user.ayamb)) user.ayamb = 0
148
+ if (!isNumber(user.ayamg)) user.ayamg = 0
149
+ if (!isNumber(user.sapir)) user.sapir = 0
150
+ if (!isNumber(user.ssapi)) user.ssapi = 0
151
+ if (!isNumber(user.esteh)) user.esteh = 0
152
+ if (!isNumber(user.leleg)) user.leleg = 0
153
+ if (!isNumber(user.leleb)) user.leleb = 0
154
+
155
+ if (!isNumber(user.ayambakar)) user.ayambakar = 0
156
+ if (!isNumber(user.gulai)) user.gulai = 0
157
+ if (!isNumber(user.rendang)) user.rendang = 0
158
+ if (!isNumber(user.ayamgoreng)) user.ayamgoreng = 0
159
+ if (!isNumber(user.oporayam)) user.oporayam = 0
160
+ if (!isNumber(user.steak)) user.steak = 0
161
+ if (!isNumber(user.babipanggang)) user.babipanggang = 0
162
+ if (!isNumber(user.ikanbakar)) user.ikanbakar = 0
163
+ if (!isNumber(user.nilabakar)) user.nilabakar = 0
164
+ if (!isNumber(user.lelebakar)) user.lelebakar = 0
165
+ if (!isNumber(user.bawalbakar)) user.bawalbakar = 0
166
+ if (!isNumber(user.udangbakar)) user.udangbakar = 0
167
+ if (!isNumber(user.pausbakar)) user.pausbakar = 0
168
+ if (!isNumber(user.kepitingbakar)) user.kepitingbakar = 0
169
+ if (!isNumber(user.soda)) user.soda = 0
170
+ if (!isNumber(user.vodka)) user.vodka = 0
171
+ if (!isNumber(user.ganja)) user.ganja = 0
172
+ if (!isNumber(user.bandage)) user.bandage = 0
173
+ if (!isNumber(user.sushi)) user.sushi = 0
174
+ if (!isNumber(user.roti)) user.roti = 0
175
+ //untuk masak
176
+ if (!isNumber(user.coal)) user.coal = 0
177
+ if (!isNumber(user.korekapi)) user.korekapi = 0
178
+ //tools
179
+ if (!isNumber(user.umpan)) user.umpan = 0
180
+
181
+ if (!isNumber(user.armor)) user.armor = 0
182
+ if (!isNumber(user.armordurability)) user.armordurability = 0
183
+ if (!isNumber(user.weapon)) user.weapon = 0
184
+ if (!isNumber(user.weapondurability)) user.weapondurability = 0
185
+ if (!isNumber(user.sword)) user.sword = 0
186
+ if (!isNumber(user.sworddurability)) user.sworddurability = 0
187
+ if (!isNumber(user.pickaxe)) user.pickaxe = 0
188
+ if (!isNumber(user.pickaxedurability)) user.pickaxedurability = 0
189
+ if (!isNumber(user.fishingrod)) user.fishingrod = 0
190
+ if (!isNumber(user.fishingroddurability)) user.fishingroddurability = 0
191
+ if (!isNumber(user.katana)) user.katana = 0
192
+ if (!isNumber(user.katanadurability)) user.katanadurability = 0
193
+ if (!isNumber(user.bow)) user.bow = 0
194
+ if (!isNumber(user.bowdurability)) user.bowdurability = 0
195
+ if (!isNumber(user.kapak)) user.kapak = 0
196
+ if (!isNumber(user.kapakdurability)) user.kapakdurability = 0
197
+ if (!isNumber(user.axe)) user.axe = 0
198
+ if (!isNumber(user.axedurability)) user.axedurability = 0
199
+ if (!isNumber(user.pisau)) user.pisau = 0
200
+ if (!isNumber(user.pisaudurability)) user.pisaudurability = 0
201
+
202
+ if (!isNumber(user.kerjasatu)) user.kerjasatu = 0
203
+ if (!isNumber(user.kerjadua)) user.kerjadua = 0
204
+ if (!isNumber(user.kerjatiga)) user.kerjatiga = 0
205
+ if (!isNumber(user.kerjaempat)) user.kerjaempat = 0
206
+ if (!isNumber(user.kerjalima)) user.kerjalima = 0
207
+ if (!isNumber(user.kerjaenam)) user.kerjaenam = 0
208
+ if (!isNumber(user.kerjatujuh)) user.kerjatujuh = 0
209
+ if (!isNumber(user.kerjadelapan)) user.kerjadelapan = 0
210
+ if (!isNumber(user.kerjasembilan)) user.kerjasembilan = 0
211
+ if (!isNumber(user.kerjasepuluh)) user.kerjasepuluh = 0
212
+ if (!isNumber(user.kerjasebelas)) user.kerjasebelas = 0
213
+ if (!isNumber(user.kerjaduabelas)) user.kerjaduabelas = 0
214
+ if (!isNumber(user.kerjatigabelas)) user.kerjatigabelas = 0
215
+ if (!isNumber(user.kerjaempatbelas)) user.kerjaempatbelas = 0
216
+ if (!isNumber(user.kerjalimabelas)) user.kerjalimabelas = 0
217
+
218
+ if (!isNumber(user.pekerjaansatu)) user.pekerjaansatu = 0
219
+ if (!isNumber(user.pekerjaandua)) user.pekerjaandua = 0
220
+ if (!isNumber(user.pekerjaantiga)) user.pekerjaantiga = 0
221
+ if (!isNumber(user.pekerjaanempat)) user.pekerjaanempat = 0
222
+ if (!isNumber(user.pekerjaanlima)) user.pekerjaanlima = 0
223
+ if (!isNumber(user.pekerjaanenam)) user.pekerjaanenam = 0
224
+ if (!isNumber(user.pekerjaantujuh)) user.pekerjaantujuh = 0
225
+ if (!isNumber(user.pekerjaandelapan)) user.pekerjaandelapan = 0
226
+ if (!isNumber(user.pekerjaansembilan)) user.pekerjaansembilan = 0
227
+ if (!isNumber(user.pekerjaansepuluh)) user.pekerjaansepuluh = 0
228
+ if (!isNumber(user.pekerjaansebelas)) user.pekerjaansebelas = 0
229
+ if (!isNumber(user.pekerjaanduabelas)) user.pekerjaanduabelas = 0
230
+ if (!isNumber(user.pekerjaantigabelas)) user.pekerjaantigabelas = 0
231
+ if (!isNumber(user.pekerjaanempatbelas)) user.pekerjaanempatbelas = 0
232
+ if (!isNumber(user.pekerjaanlimabelas)) user.pekerjaanlimabelas = 0
233
+
234
+ if (!isNumber(user.kucing)) user.kucing = 0
235
+ if (!isNumber(user.kucinglastclaim)) user.kucinglastclaim = 0
236
+ if (!isNumber(user.kucingexp)) user.kucingexp = 0
237
+ if (!isNumber(user.kuda)) user.kuda = 0
238
+ if (!isNumber(user.kudalastclaim)) user.kudalastclaim = 0
239
+ if (!isNumber(user.rubah)) user.rubah = 0
240
+ if (!isNumber(user.rubahlastclaim)) user.rubahlastclaim = 0
241
+ if (!isNumber(user.rubahexp)) user.rubahexp = 0
242
+ if (!isNumber(user.anjing)) user.anjing = 0
243
+ if (!isNumber(user.anjinglastclaim)) user.anjinglastclaim = 0
244
+ if (!isNumber(user.anjingexp)) user.anjingexp = 0
245
+ if (!isNumber(user.serigalalastclaim)) user.serigalalastclaim = 0
246
+ if (!isNumber(user.nagalastclaim)) user.nagalastclaim = 0
247
+ if (!isNumber(user.phonixlastclaim)) user.phonixlastclaim = 0
248
+ if (!isNumber(user.phonixexp)) user.phonixexp = 0
249
+ if (!isNumber(user.griffinlastclaim)) user.griffinlastclaim = 0
250
+ if (!isNumber(user.centaurlastclaim)) user.centaurlastclaim = 0
251
+
252
+ if (!isNumber(user.makananpet)) user.makananpet = 0
253
+ if (!isNumber(user.makanannaga)) user.makanannaga = 0
254
+ if (!isNumber(user.makananphonix)) user.makananphonix = 0
255
+ if (!isNumber(user.makanangriffin)) user.makanangriffin = 0
256
+ if (!isNumber(user.makananserigala)) user.makananserigala = 0
257
+ if (!isNumber(user.makanancentaur)) user.makanancentaur = 0
258
+
259
+ if (!'Banneduser' in user) user.Banneduser = false
260
+ if (!'BannedReason' in user) user.BannedReason = ''
261
+ if (!isNumber(user.warn)) user.warn = 0
262
+ if (!('banned' in user)) user.banned = false
263
+ if (!isNumber(user.bannedTime)) user.bannedTime = 0
264
+
265
+ if (!isNumber(user.afk)) user.afk = -1
266
+ if (!'afkReason' in user) user.afkReason = ''
267
+
268
+ //PET
269
+ if (!isNumber(user.healthmonster)) user.healthmonster = 0
270
+ if (!isNumber(user.anakkucing)) user.anakkucing = 0
271
+ if (!isNumber(user.anakkuda)) user.anakkuda = 0
272
+ if (!isNumber(user.anakrubah)) user.anakrubah = 0
273
+ if (!isNumber(user.anakanjing)) user.anakanjing = 0
274
+ if (!isNumber(user.serigala)) user.serigala = 0
275
+ if (!isNumber(user.serigalaexp)) user.serigalaexp = 0
276
+ if (!isNumber(user.anakserigala)) user.anakserigala = 0
277
+ if (!isNumber(user.naga)) user.naga = 0
278
+ if (!isNumber(user.anaknaga)) user.anaknaga = 0
279
+ if (!isNumber(user.phonix)) user.phonix = 0
280
+ if (!isNumber(user.anakphonix)) user.anakphonix = 0
281
+ if (!isNumber(user.griffin)) user.griffin = 0
282
+ if (!isNumber(user.anakgriffin)) user.anakgriffin = 0
283
+ if (!isNumber(user.kyubi)) user.kyubi = 0
284
+ if (!isNumber(user.anakkyubi)) user.anakkyubi = 0
285
+ if (!isNumber(user.centaur)) user.centaur = 0
286
+ if (!isNumber(user.fightnaga)) user.fightnaga = 0
287
+ if (!isNumber(user.anakcentaur)) user.anakcentaur = 0
288
+ if (!isNumber(user.makananPet)) user.makananPet = 0
289
+
290
+ if (!isNumber(user.antispam)) user.antispam = 0
291
+ if (!isNumber(user.antispamlastclaim)) user.antispamlastclaim = 0
292
+
293
+ if (!isNumber(user.kayu)) user.kayu = 0
294
+ if (!('kingdom' in user)) user.kingdom = false
295
+ if (!isNumber(user.batu)) user.batu = 0
296
+ if (!isNumber(user.ramuan)) user.ramuan = 0
297
+ if (!isNumber(user.string)) user.string = 0
298
+
299
+ //mancing
300
+ if (!isNumber(user.paus)) user.paus = 0
301
+ if (!isNumber(user.kepiting)) user.kepiting = 0
302
+ if (!isNumber(user.gurita)) user.gurita = 0
303
+ if (!isNumber(user.cumi)) user.cumi= 0
304
+ if (!isNumber(user.buntal)) user.buntal = 0
305
+ if (!isNumber(user.dory)) user.dory = 0
306
+ if (!isNumber(user.lumba)) user.lumba = 0
307
+ if (!isNumber(user.lobster)) user.lobster = 0
308
+ if (!isNumber(user.hiu)) user.hiu = 0
309
+ if (!isNumber(user.udang)) user.udang = 0
310
+ if (!isNumber(user.ikan)) user.ikan = 0
311
+ if (!isNumber(user.nila)) user.nila = 0
312
+ if (!isNumber(user.bawal)) user.bawal = 0
313
+ if (!isNumber(user.lele)) user.lele = 0
314
+ if (!isNumber(user.orca)) user.orca = 0
315
+
316
+ if (!isNumber(user.banteng)) user.banteng = 0
317
+ if (!isNumber(user.harimau)) user.harimau = 0
318
+ if (!isNumber(user.gajah)) user.gajah = 0
319
+ if (!isNumber(user.kambing)) user.kambing = 0
320
+ if (!isNumber(user.panda)) user.panda = 0
321
+ if (!isNumber(user.buaya)) user.buaya = 0
322
+ if (!isNumber(user.kerbau)) user.kerbau = 0
323
+ if (!isNumber(user.sapi)) user.sapi = 0
324
+ if (!isNumber(user.monyet)) user.monyet = 0
325
+ if (!isNumber(user.babihutan)) user.babihutan = 0
326
+ if (!isNumber(user.babi)) user.babi = 0
327
+ if (!isNumber(user.ayam)) user.ayam = 0
328
+
329
+ if (!isNumber(user.lastadventure)) user.lastadventure = 0
330
+ if (!isNumber(user.lastberburu)) user.lastberburu = 0
331
+ if (!isNumber(user.lastkill)) user.lastkill = 0
332
+ if (!isNumber(user.lastfishing)) user.lastfishing = 0
333
+ if (!isNumber(user.lastdungeon)) user.lastdungeon = 0
334
+ if (!isNumber(user.lastwar)) user.lastwar = 0
335
+ if (!isNumber(user.lastsda)) user.lastsda = 0
336
+ if (!isNumber(user.lastberbru)) user.lastberbru = 0
337
+ if (!isNumber(user.lastduel)) user.lastduel = 0
338
+ if (!isNumber(user.lastjb)) user.lastjb = 0
339
+ if (!isNumber(user.lastSetStatus)) user.lastSetStatus = 0
340
+ if (!isNumber(user.lastmining)) user.lastmining = 0
341
+ if (!isNumber(user.lasthunt)) user.lasthunt = 0
342
+ if (!isNumber(user.lasthun)) user.lasthun = 0
343
+ if (!isNumber(user.lastngocok)) user.lastngocok = 0
344
+ if (!isNumber(user.lastgift)) user.lastgift = 0
345
+ if (!isNumber(user.lastrob)) user.lastrob = 0
346
+ if (!isNumber(user.lastngojek)) user.lastngojek = 0
347
+ if (!isNumber(user.lastngewe)) user.lastngewe = 0
348
+ if (!isNumber(user.ngewe)) user.ngewe = 0
349
+ if (!isNumber(user.jualan)) user.jualan = 0
350
+ if (!isNumber(user.lastjualan)) user.lastjualan = 0
351
+ if (!isNumber(user.ngocokk)) user.ngocokk = 0
352
+ if (!isNumber(user.lastngocokk)) user.lastngocokk = 0
353
+ if (!isNumber(user.lastgrab)) user.lastgrab = 0
354
+ if (!isNumber(user.lastberkebon)) user.lastberkebon = 0
355
+ if (!isNumber(user.lastcodereg)) user.lastcodereg = 0
356
+ if (!isNumber(user.lastdagang)) user.lastdagang = 0
357
+ if (!isNumber(user.lasthourly)) user.lasthourly = 0
358
+ if (!isNumber(user.lastweekly)) user.lastweekly = 0
359
+ if (!isNumber(user.lastyearly)) user.lastyearly = 0
360
+ if (!isNumber(user.lastmonthly)) user.lastmonthly = 0
361
+ if (!isNumber(user.lastIstigfar)) user.lastIstigfar = 0
362
+ if (!isNumber(user.lastturu)) user.lastturu = 0
363
+ if (!isNumber(user.lastseen)) user.lastseen = 0
364
+ if (!isNumber(user.lastbansos)) user.lastbansos = 0
365
+ if (!isNumber(user.lastrampok)) user.lastrampok = 0
366
+ if (!('registered' in user)) user.registered = false
367
+ if (!user.registered) {
368
+ if (!('name' in user)) user.name = this.getName(m.sender)
369
+
370
+ if (!isNumber(user.apel)) user.apel = 0
371
+ if (!isNumber(user.anggur)) user.anggur = 0
372
+ if (!isNumber(user.jeruk)) user.jeruk = 0
373
+ if (!isNumber(user.semangka)) user.semangka = 0
374
+ if (!isNumber(user.mangga)) user.mangga = 0
375
+ if (!isNumber(user.stroberi)) user.stroberi = 0
376
+ if (!isNumber(user.pisang)) user.pisang = 0
377
+ if (!isNumber(user.kayu)) user.kayu = 0
378
+ if (!isNumber(user.makanan)) user.makanan = 0
379
+ if (!isNumber(user.bibitanggur)) user.bibitanggur = 0
380
+ if (!isNumber(user.bibitpisang)) user.bibitpisang = 0
381
+ if (!isNumber(user.bibitapel)) user.bibitapel = 0
382
+ if (!isNumber(user.bibitmangga)) user.bibitmangga = 0
383
+ if (!isNumber(user.bibitjeruk)) user.bibitjeruk = 0
384
+
385
+ //sambung kata
386
+ if (!isNumber(user.skata)) user.skata = 0
387
+
388
+
389
+ if (!isNumber(user.age)) user.age = -1
390
+ if (!isNumber(user.premiumDate)) user.premiumDate = -1
391
+ if (!isNumber(user.regTime)) user.regTime = -1
392
+
393
+ }
394
+ if (!isNumber(user.level)) user.level = 0
395
+ if (!user.job) user.job = 'Pengangguran'
396
+ if (!isNumber(user.jobexp)) user.jobexp = 0
397
+ if (!('jail' in user)) user.jail = false
398
+ if (!('penjara' in user)) user.penjara = false
399
+ if (!('dirawat' in user)) user.dirawat = false
400
+ if (!isNumber(user.antarpaket)) user.antarpaket = 0
401
+ if (!user.lbars) user.lbars = '[▒▒▒▒▒▒▒▒▒]'
402
+ if (!user.premium) user.premium = false
403
+ if (!user.premiumTime) user.premiumTime= 0
404
+ if (!user.vip) user.vip = 'tidak'
405
+ if (!isNumber(user.vipPoin)) user.vipPoin = 0
406
+ if (!user.role) user.role = 'Newbie ㋡'
407
+ if (!('autolevelup' in user)) user.autolevelup = true
408
+ if (!('lastIstigfar' in user)) user.lastIstigfar = true
409
+
410
+ //demon slayer dan rpg baru
411
+ if (!("skill" in user)) user.skill = ""
412
+ if (!("korps" in user)) user.korps = ""
413
+ if (!("korpsgrade" in user)) user.korpsgrade = ""
414
+ if (!("breaths" in user)) user.breaths = ""
415
+ if (!("magic" in user)) user.magic = ""
416
+ if (!("demon" in user)) user.demon = ""
417
+ if (!isNumber(user.darahiblis)) user.darahiblis = 0
418
+ if (!isNumber(user.demonblood)) user.demonblood = 0
419
+ if (!isNumber(user.demonkill)) user.demonkill = 0
420
+ if (!isNumber(user.hashirakill)) user.hashirakill = 0
421
+ if (!isNumber(user.alldemonkill)) user.alldemonkill = 0
422
+ if (!isNumber(user.allhashirakill)) user.allhashirakill = 0
423
+ if (!isNumber(user.attack)) user.attack = 0
424
+ if (!isNumber(user.strenght)) user.strenght = 0
425
+ if (!isNumber(user.speed)) user.speed = 0
426
+ if (!isNumber(user.defense)) user.defense = 0
427
+ if (!isNumber(user.regeneration)) user.regeneration = 0
428
+ if (!isNumber(user.dana)) user.dana = 0
429
+ if (!isNumber(user.gopay)) user.gopay = 0
430
+ if (!isNumber(user.ovo)) user.ovo = 0
431
+ if (!isNumber(user.lastngaji)) user.lastngaji = 0
432
+ if (!isNumber(user.lastlonte)) user.lastlonte = 0
433
+ if (!isNumber(user.lastkoboy)) user.lastkoboy = 0
434
+ if (!isNumber(user.lastdate)) user.lastdate = 0
435
+ if (!isNumber(user.lasttambang)) user.lasttambang = 0
436
+ if (!isNumber(user.lastngepet)) user.lastngepet = 0
437
+ if (!isNumber(user.lasttaxi)) user.lasttaxi = 0
438
+ if (!isNumber(user.taxi)) user.taxi = 0
439
+ if (!isNumber(user.lastyoutuber)) user.lastyoutuber = 0
440
+ if (!isNumber(user.subscribers)) user.subscribers = 0
441
+ if (!isNumber(user.viewers)) user.viewers = 0
442
+ if (!isNumber(user.like)) user.like = 0
443
+ if (!isNumber(user.playButton)) user.playButton = 0
444
+
445
+ } else global.db.data.users[m.sender] = {
446
+ taxi: 0,
447
+ lasttaxi: 0,
448
+ lastyoutuber: 0,
449
+ subscribers: 0,
450
+ viewers: 0,
451
+ like: 0,
452
+ playButton: 0,
453
+ saldo: 0,
454
+ pengeluaran: 0,
455
+ healt: 100,
456
+ health: 100,
457
+ energi: 100,
458
+ power: 100,
459
+ title: '',
460
+ haus: 100,
461
+ laper: 100,
462
+ tprem: 0,
463
+ stamina : 100,
464
+ level: 0,
465
+ follow: 0,
466
+ lastfollow: 0,
467
+ followers: 0,
468
+ pasangan: '',
469
+ sahabat: '',
470
+ location: 'Gubuk',
471
+ titlein: 'Belum Ada',
472
+ ultah: '',
473
+ waifu: 'Belum Di Set',
474
+ husbu: 'Belum Di Set',
475
+ pc : 0,
476
+ exp: 0,
477
+ coin: 0,
478
+ atm: 0,
479
+ limit: 100,
480
+ skata: 0,
481
+ tigame: 999,
482
+ lastclaim: 0,
483
+ judilast: 0,
484
+ lastnambang: 0,
485
+ lastnebang: 0,
486
+ lastmulung: 0,
487
+ lastkerja: 0,
488
+ lastmaling: 0,
489
+ lastbunuhi: 0,
490
+ lastbisnis: 0,
491
+ lastberbisnis: 0,
492
+ bisnis: 0,
493
+ berbisnis: 0,
494
+ lastmancing: 0,
495
+ pancing: 0,
496
+ pancingan: 0,
497
+ totalPancingan: 0,
498
+ kardus: 0,
499
+ botol: 0,
500
+ kaleng: 0,
501
+ money: 0,
502
+ litecoin: 0,
503
+ chip: 0,
504
+ tiketcoin: 0,
505
+ poin: 0,
506
+ bank: 0,
507
+ balance: 0,
508
+ diamond: 0,
509
+ emerald: 0,
510
+ rock: 0,
511
+ wood: 0,
512
+ berlian: 0,
513
+ iron: 0,
514
+ emas: 0,
515
+ common: 0,
516
+ uncommon: 0,
517
+ mythic: 0,
518
+ legendary: 0,
519
+ rumahsakit: 0,
520
+ tambang: 0,
521
+ camptroops: 0,
522
+ pertanian: 0,
523
+ fortress: 0,
524
+ trofi: 0,
525
+ rtrofi: 'perunggu',
526
+ makanan: 0,
527
+ troopcamp: 0,
528
+ shield: 0,
529
+ arlok: 0,
530
+ ojekk: 0,
531
+ ojek: 0,
532
+ lastngewe: 0,
533
+ ngewe: 0,
534
+ polisi: 0,
535
+ pedagang: 0,
536
+ dokter: 0,
537
+ petani: 0,
538
+ montir: 0,
539
+ kuli: 0,
540
+ korbanngocok: 0,
541
+ //+ stamina
542
+ coal: 0,
543
+ korekapi: 0,
544
+ ayambakar: 0,
545
+ gulai: 0,
546
+ rendang: 0,
547
+ ayamgoreng: 0,
548
+ oporayam: 0,
549
+ steak: 0,
550
+ babipanggang: 0,
551
+ ikanbakar: 0,
552
+ lelebakar: 0,
553
+ nilabakar: 0,
554
+ bawalbakar: 0,
555
+ udangbakar: 0,
556
+ pausbakar: 0,
557
+ kepitingbakar: 0,
558
+ soda: 0,
559
+ vodka: 0,
560
+ ganja: 0,
561
+ bandage: 0,
562
+ sushi: 0,
563
+ roti: 0,
564
+ //meracik
565
+ ramuan: 0,
566
+ lastramuanclaim: 0,
567
+ gems: 0,
568
+ cupon: 0,
569
+ lastgemsclaim: 0,
570
+ eleksirb: 0,
571
+ penduduk: 0,
572
+ archer: 0,
573
+ shadow: 0,
574
+ laststringclaim: 0,
575
+ lastpotionclaim: 0,
576
+ lastswordclaim: 0,
577
+ lastweaponclaim: 0,
578
+ lastironclaim: 0,
579
+ lastmancingclaim: 0,
580
+ anakpancingan: 0,
581
+ //mancing
582
+ as: 0,
583
+ paus: 0,
584
+ kepiting: 0,
585
+ gurita: 0,
586
+ cumi: 0,
587
+ buntal: 0,
588
+ dory: 0,
589
+ lumba: 0,
590
+ lobster: 0,
591
+ hiu: 0,
592
+ lele: 0,
593
+ nila: 0,
594
+ bawal: 0,
595
+ udang: 0,
596
+ ikan: 0,
597
+ orca: 0,
598
+ banteng: 0,
599
+ harimau: 0,
600
+ gajah: 0,
601
+ kambing: 0,
602
+ panda: 0,
603
+ buaya: 0,
604
+ kerbau : 0,
605
+ sapi: 0,
606
+ monyet : 0,
607
+ babihutan: 0,
608
+ babi: 0,
609
+ ayam: 0,
610
+ apel: 20,
611
+ ayamb: 0,
612
+ ayamg: 0,
613
+ ssapi: 0,
614
+ sapir: 0,
615
+ leleb: 0,
616
+ leleg: 0,
617
+ esteh: 0,
618
+ pet: 0,
619
+ potion: 0,
620
+ sampah: 0,
621
+ kucing: 0,
622
+ kucinglastclaim: 0,
623
+ kucingexp: 0,
624
+ kuda: 0,
625
+ kudalastclaim: 0,
626
+ rubah: 0,
627
+ rubahlastclaim: 0,
628
+ rubahexp: 0,
629
+ anjing: 0,
630
+ anjinglastclaim: 0,
631
+ anjingexp: 0,
632
+ naga: 0,
633
+ nagalastclaim: 0,
634
+ griffin: 0,
635
+ griffinlastclaim: 0,
636
+ centaur: 0,
637
+ fightnaga: 0,
638
+ centaurlastclaim: 0,
639
+ serigala: 0,
640
+ serigalalastclaim: 0,
641
+ serigalaexp: 0,
642
+ phonix: 0,
643
+ phonixlastclaim: 0,
644
+ phonixexp : 0,
645
+ makanannaga: 0,
646
+ makananphonix: 0,
647
+ makanancentaur: 0,
648
+ makananserigala: 0,
649
+
650
+ Banneduser: false,
651
+ BannedReason: '',
652
+ banned: false,
653
+ bannedTime: 0,
654
+ warn: 0,
655
+ afk: -1,
656
+ afkReason: '',
657
+ anakkucing: 0,
658
+ anakkuda: 0,
659
+ anakrubah: 0,
660
+ anakanjing: 0,
661
+ makananpet: 0,
662
+ makananPet: 0,
663
+ antispam: 0,
664
+ antispamlastclaim: 0,
665
+ kayu: 0,
666
+ batu: 0,
667
+ string: 0,
668
+ umpan: 0,
669
+ armor: 0,
670
+ armordurability: 0,
671
+ weapon: 0,
672
+ weapondurability: 0,
673
+ sword: 0,
674
+ sworddurability: 0,
675
+ pickaxe: 0,
676
+ pickaxedurability: 0,
677
+ fishingrod: 0,
678
+ fishingroddurability: 0,
679
+ katana: 0,
680
+ katanadurability: 0,
681
+ bow: 0,
682
+ bowdurability: 0,
683
+ kapak: 0,
684
+ kapakdurability: 0,
685
+ axe: 0,
686
+ axedurability: 0,
687
+ pisau: 0,
688
+ pisaudurability: 0,
689
+ kerjasatu: 0,
690
+ kerjadua: 0,
691
+ kerjatiga: 0,
692
+ kerjaempat: 0,
693
+ kerjalima: 0,
694
+ kerjaenam: 0,
695
+ kerjatujuh: 0,
696
+ kerjadelapan: 0,
697
+ kerjasembilan: 0,
698
+ kerjasepuluh: 0,
699
+ kerjasebelas: 0,
700
+ kerjaduabelas: 0,
701
+ kerjatigabelas: 0,
702
+ kerjaempatbelas: 0,
703
+ kerjalimabelas: 0,
704
+ pekerjaansatu: 0,
705
+ pekerjaandua: 0,
706
+ pekerjaantiga: 0,
707
+ pekerjaanempat: 0,
708
+ pekerjaanlima: 0,
709
+ pekerjaanenam: 0,
710
+ pekerjaantujuh: 0,
711
+ pekerjaandelapan: 0,
712
+ pekerjaansembilan: 0,
713
+ pekerjaansepuluh: 0,
714
+ pekerjaansebelas: 0,
715
+ pekerjaanduabelas: 0,
716
+ pekerjaantigabelas: 0,
717
+ pekerjaanempatbelas: 0,
718
+ pekerjaanlimabelas: 0,
719
+ lastadventure: 0,
720
+ lastwar: 0,
721
+ lastberkebon: 0,
722
+ lastberburu: 0,
723
+ lastbansos: 0,
724
+ lastrampok: 0,
725
+ lastkill: 0,
726
+ lastfishing: 0,
727
+ lastdungeon: 0,
728
+ lastduel: 0,
729
+ lastmining: 0,
730
+ lasthourly: 0,
731
+ lastdagang: 0,
732
+ lasthunt: 0,
733
+ lasthun : 0,
734
+ lastweekly: 0,
735
+ lastmonthly: 0,
736
+ lastyearly: 0,
737
+ lastjb: 0,
738
+ lastrob: 0,
739
+ lastdaang: 0,
740
+ lastngojek: 0,
741
+ lastgrab: 0,
742
+ lastngocok: 0,
743
+ lastturu: 0,
744
+ lastseen: 0,
745
+ lastSetStatus: 0,
746
+ registered: false,
747
+ apel: 20,
748
+ mangga: 0,
749
+ stroberi: 0,
750
+ semangka: 0,
751
+ jeruk: 0,
752
+ semangka: 0,
753
+ name: this.getName(m.sender),
754
+ age: -1,
755
+ regTime: -1,
756
+ premiumDate: -1,
757
+ premium: false,
758
+ premiumTime: 0,
759
+ vip: 'tidak',
760
+ vipPoin: 0,
761
+ job: 'Pengangguran',
762
+ jobexp: 0,
763
+ jail: false,
764
+ penjara: false,
765
+ antarpaket: 0,
766
+ dirawat: false,
767
+ lbars: '[▒▒▒▒▒▒▒▒▒]',
768
+ role: 'Newbie ㋡',
769
+ registered: false,
770
+ name: this.getName(m.sender),
771
+ age: -1,
772
+ regTime: -1,
773
+ autolevelup: true,
774
+ lastIstigfar: 0,
775
+
776
+ skill: "",
777
+ korps: "",
778
+ korpsgrade: "",
779
+ demon: "",
780
+ breaths: "",
781
+ magic: "",
782
+ darahiblis: 0,
783
+ demonblood: 0,
784
+ demonkill: 0,
785
+ hashirakill: 0,
786
+ alldemonkill: 0,
787
+ allhashirakill: 0,
788
+ attack: 0,
789
+ speed: 0,
790
+ strenght: 0,
791
+ defense: 0,
792
+ regeneration: 0,
793
+ ovo: 0,
794
+ dana: 0,
795
+ gopay: 0,
796
+ lastngaji: 0,
797
+ lastlonte: 0,
798
+ lastkoboy: 0,
799
+ lastdate: 0,
800
+ lasttambang: 0,
801
+ lastngepet: 0,
802
+ }
803
+ let chat = global.db.data.chats[m.chat]
804
+ if (typeof chat !== 'object') global.db.data.chats[m.chat] = {}
805
+ if (chat) {
806
+ if (!('isBanned' in chat)) chat.isBanned = false
807
+ if (!('welcome' in chat)) chat.welcome = true
808
+ if (!isNumber(chat.welcometype)) chat.welcometype = 1
809
+ if (!('detect' in chat)) chat.detect = false
810
+ if (!('isBannedTime' in chat)) chat.isBannedTime = false
811
+ if (!('mute' in chat)) chat.mute = false
812
+ if (!('listStr' in chat)) chat.listStr = {}
813
+ if (!('sWelcome' in chat)) chat.sWelcome = 'Hai, @user!\nSelamat datang di grup @subject\n\n@desc'
814
+ if (!('sBye' in chat)) chat.sBye = 'Selamat tinggal @user!'
815
+ if (!('sPromote' in chat)) chat.sPromote = ''
816
+ if (!('sDemote' in chat)) chat.sDemote = ''
817
+ if (!('delete' in chat)) chat.delete = true
818
+ if (!('antiLink' in chat)) chat.antiLink = true
819
+ if (!('antiLinknokick' in chat)) chat.antiLinknokick = false
820
+ if (!('antiSticker' in chat)) chat.antiSticker = false
821
+ if (!('antiStickernokick' in chat)) chat.antiStickernokick = false
822
+ if (!('viewonce' in chat)) chat.viewonce = false
823
+ if (!('antiToxic' in chat)) chat.antiToxic = false
824
+ if (!isNumber(chat.expired)) chat.expired = 0
825
+ if (!("memgc" in chat)) chat.memgc = {}
826
+ if (!('antilinkig' in chat)) chat.antilinkig = false
827
+ if (!('antilinkignokick' in chat)) chat.antilinkignokick = false
828
+ if (!('antilinkfb' in chat)) chat.antilinkfb = false
829
+ if (!('antilinkfbnokick' in chat)) chat.antilinkfbnokick = false
830
+ if (!('antilinktwit' in chat)) chat.antilinktwit = false
831
+ if (!('antilinktwitnokick' in chat)) chat.antilinktwitnokick = false
832
+ if (!('antilinkyt' in chat)) chat.antilinkyt = false
833
+ if (!('antilinkytnokick' in chat)) chat.antilinkytnokick = false
834
+ if (!('antilinktele' in chat)) chat.antilinktele = false
835
+ if (!('antilinktelenokick' in chat)) chat.antilinktelenokick = false
836
+ if (!('antilinkwame' in chat)) chat.antilinkwame = false
837
+ if (!('antilinkwamenokick' in chat)) chat.antilinkwamenokick = false
838
+ if (!('antilinkall' in chat)) chat.antilinkall = false
839
+ if (!('antilinkallnokick' in chat)) chat.antilinkallnokick = false
840
+ if (!('antilinktt' in chat)) chat.antilinktt = false
841
+ if (!('antilinkttnokick' in chat)) chat.antilinkttnokick = false
842
+ if (!('antibot' in chat)) chat.antibot = false
843
+ } else global.db.data.chats[m.chat] = {
844
+ isBanned: false,
845
+ welcome: true,
846
+ welcometype: 1,
847
+ detect: false,
848
+ isBannedTime: false,
849
+ mute: false,
850
+ listStr: {},
851
+ sWelcome: 'Hai, @user!\nSelamat datang di grup @subject\n\n@desc',
852
+ sBye: 'Selamat tinggal @user!',
853
+ sPromote: '',
854
+ sDemote: '',
855
+ delete: false,
856
+ antiLink: false,
857
+ antiLinknokick: false,
858
+ antiSticker: false,
859
+ antiStickernokick: false,
860
+ viewonce: false,
861
+ antiToxic: true,
862
+ antilinkig: false,
863
+ antilinkignokick: false,
864
+ antilinkyt: false,
865
+ antilinkytnokick: false,
866
+ antilinktwit: false,
867
+ antilinktwitnokick: false,
868
+ antilinkfb: false,
869
+ antilinkfbnokick: false,
870
+ antilinkall: false,
871
+ antilinkallnokick: false,
872
+ antilinkwame: false,
873
+ antilinkwamenokick: false,
874
+ antilinktele: false,
875
+ antilinktelenokick: false,
876
+ antilinktt: false,
877
+ antilinkttnokick: false,
878
+ antibot: false,
879
+ rpg: false,
880
+ }
881
+ let memgc = global.db.data.chats[m.chat].memgc[m.sender]
882
+ if (typeof memgc !== 'object') global.db.data.chats[m.chat].memgc[m.sender] = {}
883
+ if (memgc) {
884
+ if (!('blacklist' in memgc)) memgc.blacklist = false
885
+ if (!('banned' in memgc)) memgc.banned = false
886
+ if (!isNumber(memgc.bannedTime)) memgc.bannedTime = 0
887
+ if (!isNumber(memgc.chat)) memgc.chat = 0
888
+ if (!isNumber(memgc.chatTotal)) memgc.chatTotal = 0
889
+ if (!isNumber(memgc.command)) memgc.command = 0
890
+ if (!isNumber(memgc.commandTotal)) memgc.commandTotal = 0
891
+ if (!isNumber(memgc.lastseen)) memgc.lastseen = 0
892
+ } else global.db.data.chats[m.chat].memgc[m.sender] = {
893
+ blacklist: false,
894
+ banned: false,
895
+ bannedTime: 0,
896
+ chat: 0,
897
+ chatTotal: 0,
898
+ command: 0,
899
+ commandTotal: 0,
900
+ lastseen: 0
901
+ }
902
+ } catch (e) {
903
+ console.error(e)
904
+ }
905
+ if (opts['nyimak']) return
906
+ if (!m.fromMe && opts['self']) return
907
+ if (opts['pconly'] && m.chat.endsWith('g.us')) return
908
+ if (opts['gconly'] && !m.chat.endsWith('g.us')) return
909
+ if (opts['swonly'] && m.chat !== 'status@broadcast') return
910
+ if (typeof m.text !== 'string') m.text = ''
911
+ if (opts['queque'] && m.text) {
912
+ this.msgqueque.push(m.id || m.key.id)
913
+ await delay(this.msgqueque.length * 1000)
914
+ }
915
+ for (let name in global.plugins) {
916
+ let plugin = global.plugins[name]
917
+ if (!plugin) continue
918
+ if (plugin.disabled) continue
919
+ if (!plugin.all) continue
920
+ if (typeof plugin.all !== 'function') continue
921
+ try {
922
+ await plugin.all.call(this, m, chatUpdate)
923
+ } catch (e) {
924
+ if (typeof e === 'string') continue
925
+ console.error(e)
926
+ }
927
+ }
928
+ if (m.id.startsWith('BAE5') && m.id.length === 16 || m.isBaileys && m.fromMe) return
929
+ m.exp += Math.ceil(Math.random() * 10)
930
+
931
+ let usedPrefix
932
+ let _user = global.db.data && global.db.data.users && global.db.data.users[m.sender]
933
+
934
+ let isROwner = [global.conn.user.jid, ...global.owner].map(v => v.replace(/[^0-9]/g, '') + '@s.whatsapp.net').includes(m.sender)
935
+ let isOwner = isROwner || m.fromMe
936
+ let isMods = isOwner || global.mods.map(v => v.replace(/[^0-9]/g, '') + '@s.whatsapp.net').includes(m.sender)
937
+ let isPrems = isROwner || (db.data.users[m.sender].premiumTime > 0 || db.data.users[m.sender].premium)
938
+ let groupMetadata = (m.isGroup ? (conn.chats[m.chat] || {}).metadata : {}) || {}
939
+ let participants = (m.isGroup ? groupMetadata.participants : []) || []
940
+ let user = (m.isGroup ? participants.find(u => conn.decodeJid(u.id) === m.sender) : {}) || {} // User Data
941
+ let bot = (m.isGroup ? participants.find(u => conn.decodeJid(u.id) == this.user.jid) : {}) || {} // Your Data
942
+ let isAdmin = user && user.admin || false // Is User Admin?
943
+ let isBotAdmin = bot && bot.admin || false // Are you Admin?
944
+ for (let name in global.plugins) {
945
+ let plugin = global.plugins[name]
946
+ if (!plugin) continue
947
+ if (plugin.disabled) continue
948
+ if (!opts['restrict']) if (plugin.tags && plugin.tags.includes('admin')) {
949
+ // global.dfail('restrict', m, this)
950
+ continue
951
+ }
952
+ const str2Regex = str => str.replace(/[|\\{}()[\]^$+*?.]/g, '\\$&')
953
+ let _prefix = plugin.customPrefix ? plugin.customPrefix : conn.prefix ? conn.prefix : global.prefix
954
+ let match = (_prefix instanceof RegExp ? // RegExp Mode?
955
+ [[_prefix.exec(m.text), _prefix]] :
956
+ Array.isArray(_prefix) ? // Array?
957
+ _prefix.map(p => {
958
+ let re = p instanceof RegExp ? // RegExp in Array?
959
+ p :
960
+ new RegExp(str2Regex(p))
961
+ return [re.exec(m.text), re]
962
+ }) :
963
+ typeof _prefix === 'string' ? // String?
964
+ [[new RegExp(str2Regex(_prefix)).exec(m.text), new RegExp(str2Regex(_prefix))]] :
965
+ [[[], new RegExp]]
966
+ ).find(p => p[1])
967
+ if (typeof plugin.before === 'function') if (await plugin.before.call(this, m, {
968
+ match,
969
+ conn: this,
970
+ participants,
971
+ groupMetadata,
972
+ user,
973
+ bot,
974
+ isROwner,
975
+ isOwner,
976
+ isAdmin,
977
+ isBotAdmin,
978
+ isPrems,
979
+ chatUpdate,
980
+ })) continue
981
+ if (typeof plugin !== 'function') continue
982
+ if ((usedPrefix = (match[0] || '')[0])) {
983
+ let noPrefix = m.text.replace(usedPrefix, '')
984
+ let [command, ...args] = noPrefix.trim().split` `.filter(v => v)
985
+ args = args || []
986
+ let _args = noPrefix.trim().split` `.slice(1)
987
+ let text = _args.join` `
988
+ command = (command || '').toLowerCase()
989
+ let fail = plugin.fail || global.dfail // When failed
990
+ let isAccept = plugin.command instanceof RegExp ? // RegExp Mode?
991
+ plugin.command.test(command) :
992
+ Array.isArray(plugin.command) ? // Array?
993
+ plugin.command.some(cmd => cmd instanceof RegExp ? // RegExp in Array?
994
+ cmd.test(command) :
995
+ cmd === command
996
+ ) :
997
+ typeof plugin.command === 'string' ? // String?
998
+ plugin.command === command :
999
+ false
1000
+
1001
+ if (!isAccept) continue
1002
+ m.plugin = name
1003
+ if (m.chat in global.db.data.chats || m.sender in global.db.data.users) {
1004
+ let chat = global.db.data.chats[m.chat]
1005
+ let user = global.db.data.users[m.sender]
1006
+ if (name != 'group-modebot.js' && name != 'owner-unbanchat.js' && name != 'owner-exec.js' && name != 'owner-exec2.js' && name != 'tool-delete.js' && (chat?.isBanned || chat?.mute))
1007
+ return
1008
+ if (name != 'unbanchat.js' && chat && chat.isBanned) return // Except this
1009
+ if (name != 'unbanuser.js' && user && user.banned) return
1010
+ if (m.isGroup) {
1011
+ chat.memgc[m.sender].command++
1012
+ chat.memgc[m.sender].commandTotal++
1013
+ chat.memgc[m.sender].lastCmd = Date.now()
1014
+ }
1015
+ user.command++
1016
+ user.commandTotal++
1017
+ user.lastCmd = Date.now()
1018
+ }
1019
+
1020
+ if (plugin.rowner && plugin.owner && !(isROwner || isOwner)) { // Both Owner
1021
+ fail('owner', m, this)
1022
+ continue
1023
+ }
1024
+ if (plugin.rowner && !isROwner) { // Real Owner
1025
+ fail('rowner', m, this)
1026
+ continue
1027
+ }
1028
+ if (plugin.owner && !isOwner) { // Number Owner
1029
+ fail('owner', m, this)
1030
+ continue
1031
+ }
1032
+ if (plugin.mods && !isMods) { // Moderator
1033
+ fail('mods', m, this)
1034
+ continue
1035
+ }
1036
+ if (plugin.premium && !isPrems) { // Premium
1037
+ fail('premium', m, this)
1038
+ continue
1039
+ }
1040
+ if (plugin.group && !m.isGroup) { // Group Only
1041
+ fail('group', m, this)
1042
+ continue
1043
+ } else if (plugin.botAdmin && !isBotAdmin) { // You Admin
1044
+ fail('botAdmin', m, this)
1045
+ continue
1046
+ } else if (plugin.admin && !isAdmin) { // User Admin
1047
+ fail('admin', m, this)
1048
+ continue
1049
+ }
1050
+ if (plugin.private && m.isGroup) { // Private Chat Only
1051
+ fail('private', m, this)
1052
+ continue
1053
+ }
1054
+ if (plugin.register == true && _user.registered == false) { // Butuh daftar?
1055
+ fail('unreg', m, this)
1056
+ continue
1057
+ }
1058
+ m.isCommand = true
1059
+ let xp = 'exp' in plugin ? parseInt(plugin.exp) : 17 // XP Earning per command
1060
+ if (xp > 200) m.reply('Ngecit -_-') // Hehehe
1061
+ else m.exp += xp
1062
+ if (!isPrems && plugin.limit && global.db.data.users[m.sender].limit < plugin.limit * 1) {
1063
+ this.reply(m.chat, `Limit anda habis, silahkan beli melalui *${usedPrefix}buy* atau beli di *${usedPrefix}shop*`, m)
1064
+ continue // Limit habis
1065
+ }
1066
+ if (plugin.level > _user.level) {
1067
+ this.reply(m.chat, `diperlukan level ${plugin.level} untuk menggunakan perintah ini. Level kamu ${_user.level}\m gunakan .levelup untuk menaikan level!`, m)
1068
+ continue // If the level has not been reached
1069
+ }
1070
+ let extra = {
1071
+ match,
1072
+ usedPrefix,
1073
+ noPrefix,
1074
+ _args,
1075
+ args,
1076
+ command,
1077
+ text,
1078
+ conn: this,
1079
+ participants,
1080
+ groupMetadata,
1081
+ user,
1082
+ bot,
1083
+ isROwner,
1084
+ isOwner,
1085
+ isAdmin,
1086
+ isBotAdmin,
1087
+ isPrems,
1088
+ chatUpdate,
1089
+ }
1090
+ try {
1091
+ await plugin.call(this, m, extra)
1092
+ if (!isPrems) m.limit = m.limit || plugin.limit || false
1093
+ } catch (e) {
1094
+ // Error occured
1095
+ m.error = e
1096
+ console.error(e)
1097
+ if (e) {
1098
+ let text = util.format(e)
1099
+ for (let key of Object.values(APIKeys))
1100
+ text = text.replace(new RegExp(key, 'g'), '#HIDDEN#')
1101
+ if (e.name)
1102
+ for (let jid of owner.map(v => v.replace(/[^0-9]/g, '') + '@s.whatsapp.net').filter(v => v != this.user.jid)) {
1103
+ let data = (await this.onWhatsApp(jid))[0] || {}
1104
+ if (data.exists)
1105
+ m.reply(`*Plugin:* ${m.plugin}\n*Sender:* @${m.sender.split`@`[0]}\n*Chat:* ${m.chat}\n*Chat Name:* ${await this.getName(m.chat)}\n*Command:* ${usedPrefix}${command} ${args.join(' ')}\n\n\`\`\`${text}\`\`\``.trim(), data.jid, { mentions: [m.sender] })
1106
+ }
1107
+ m.reply(text)
1108
+ }
1109
+ } finally {
1110
+ // m.reply(util.format(_user))
1111
+ if (typeof plugin.after === 'function') {
1112
+ try {
1113
+ await plugin.after.call(this, m, extra)
1114
+ } catch (e) {
1115
+ console.error(e)
1116
+ }
1117
+ }
1118
+ if (m.limit) m.reply(+ m.limit + ' Limit terpakai')
1119
+ }
1120
+ break
1121
+ }
1122
+ }
1123
+ } catch (e) {
1124
+ console.error(e)
1125
+ } finally {
1126
+ //conn.sendPresenceUpdate('composing', m.chat) // kalo pengen auto vn hapus // di baris dekat conn
1127
+ //console.log(global.db.data.users[m.sender])
1128
+ let user, stats = global.db.data.stats
1129
+ if (m) {
1130
+ if (m.sender && (user = global.db.data.users[m.sender])) {
1131
+ user.exp += m.exp
1132
+ user.limit -= m.limit * 1
1133
+ }
1134
+
1135
+ let stat
1136
+ if (m.plugin) {
1137
+ let now = + new Date
1138
+ if (m.plugin in stats) {
1139
+ stat = stats[m.plugin]
1140
+ if (!isNumber(stat.total)) stat.total = 1
1141
+ if (!isNumber(stat.success)) stat.success = m.error != null ? 0 : 1
1142
+ if (!isNumber(stat.last)) stat.last = now
1143
+ if (!isNumber(stat.lastSuccess)) stat.lastSuccess = m.error != null ? 0 : now
1144
+ } else stat = stats[m.plugin] = {
1145
+ total: 1,
1146
+ success: m.error != null ? 0 : 1,
1147
+ last: now,
1148
+ lastSuccess: m.error != null ? 0 : now
1149
+ }
1150
+ stat.total += 1
1151
+ stat.last = now
1152
+ if (m.error == null) {
1153
+ stat.success += 1
1154
+ stat.lastSuccess = now
1155
+ }
1156
+ }
1157
+ }
1158
+
1159
+ try {
1160
+ require('./lib/print')(m, this)
1161
+ } catch (e) {
1162
+ console.log(m, m.quoted, e)
1163
+ }
1164
+ if (opts['autoread']) await this.readMessages([m.key])
1165
+ }
1166
+ },
1167
+
1168
+ async participantsUpdate({ id, participants, action }) {
1169
+ if (opts['self']) return
1170
+ // if (id in conn.chats) return // First login will spam
1171
+ if (global.isInit) return
1172
+ let chat = db.data.chats[id] || {}
1173
+ let text = ''
1174
+ switch (action) {
1175
+ case 'add':
1176
+ case 'remove':
1177
+ case 'leave':
1178
+ case 'invite':
1179
+ case 'invite_v4':
1180
+ if (chat.welcome) {
1181
+ let groupMetadata = await this.groupMetadata(id) || (conn.chats[id] || {}).metadata
1182
+ for (let user of participants) {
1183
+ let pp = 'https://btch.pages.dev/file/70e8de9b1879568954f09.jpg'
1184
+ try {
1185
+ pp = await this.profilePictureUrl(user, 'image')
1186
+ } catch (e) {
1187
+ } finally {
1188
+ text = (action === 'add' ? (chat.sWelcome || this.welcome || conn.welcome || 'Welcome, @user!').replace('@subject', await this.getName(id)).replace('@desc', groupMetadata.desc ? groupMetadata.desc.toString() : '') :
1189
+ (chat.sBye || this.bye || conn.bye || 'Bye, @user!')).replace('@user', '@' + user.split('@')[0])
1190
+ this.sendMessage(id, {
1191
+ text: text,
1192
+ contextInfo: {
1193
+ mentionedJid: [user],
1194
+ externalAdReply: {
1195
+ title: global.wm,
1196
+ body: '',
1197
+ thumbnailUrl: pp,
1198
+ sourceUrl: 'https://chat.whatsapp.com/KIcqnzY4NJMHXPTz8Xopvd',
1199
+ mediaType: 1,
1200
+ renderLargerThumbnail: true
1201
+ }}}, { quoted: null })
1202
+ }
1203
+ }
1204
+ }
1205
+ break
1206
+ case 'promote':
1207
+ text = (chat.sPromote || this.spromote || conn.spromote || '@user ```is now Admin```')
1208
+ case 'demote':
1209
+ if (!text) text = (chat.sDemote || this.sdemote || conn.sdemote || '@user ```is no longer Admin```')
1210
+ text = text.replace('@user', '@' + participants[0].split('@')[0])
1211
+ if (chat.detect) this.sendMessage(id, text, {
1212
+ contextInfo: {
1213
+ mentionedJid: this.parseMention(text)
1214
+ }
1215
+ })
1216
+ break
1217
+ }
1218
+ },
1219
+ async delete({ remoteJid, fromMe, id, participant }) {
1220
+ /*if (fromMe) return
1221
+ let chats = Object.entries(conn.chats).find(([user, data]) => data.messages && data.messages[id])
1222
+ if (!chats) return
1223
+ let msg = JSON.parse(chats[1].messages[id])
1224
+ let chat = global.db.data.chats[msg.key.remoteJid] || {}
1225
+ if (chat.delete) return
1226
+ await this.reply(msg.key.remoteJid, `
1227
+ Terdeteksi @${participant.split`@`[0]} telah menghapus pesan
1228
+ Untuk mematikan fitur ini, ketik
1229
+ *.enable delete*
1230
+ `.trim(), msg, {
1231
+ mentions: [participant]
1232
+ })
1233
+ this.copyNForward(msg.key.remoteJid, msg).catch(e => console.log(e, msg))*/
1234
+ }
1235
+ }
1236
+
1237
+ global.dfail = (type, m, conn) => {
1238
+ let msg = {
1239
+ rowner: 'Perintah ini hanya dapat digunakan oleh _*OWWNER!1!1!*_',
1240
+ owner: 'Perintah ini hanya dapat digunakan oleh _*Owner Bot*_!',
1241
+ mods: 'Perintah ini hanya dapat digunakan oleh _*Moderator*_ !',
1242
+ premium: 'Perintah ini hanya untuk member _*Premium*_ !',
1243
+ group: 'Perintah ini hanya dapat digunakan di grup!',
1244
+ private: 'Perintah ini hanya dapat digunakan di Chat Pribadi!',
1245
+ admin: 'Perintah ini hanya untuk *Admin* grup!',
1246
+ botAdmin: 'Jadikan bot sebagai *Admin* untuk menggunakan perintah ini!',
1247
+ unreg: 'Silahkan daftar untuk menggunakan fitur ini dengan cara mengetik:\n\n*#daftar nama.umur*\n\nContoh: *#daftar Mansur.16*',
1248
+ restrict: 'Fitur ini di *disable*!'
1249
+ }[type]
1250
+ if (msg) return m.reply(msg)
1251
+ }
1252
+
1253
+ let fs = require('fs')
1254
+ let chalk = require('chalk')
1255
+ let file = require.resolve(__filename)
1256
+ fs.watchFile(file, () => {
1257
+ fs.unwatchFile(file)
1258
+ console.log(chalk.redBright("Update 'handler.js'"))
1259
+ delete require.cache[file]
1260
+ if (global.reloadHandler) console.log(global.reloadHandler())
1261
+ })
heroku.yml ADDED
@@ -0,0 +1,3 @@
 
 
 
 
1
+ build:
2
+ docker:
3
+ web: Dockerfile
index.js ADDED
@@ -0,0 +1,121 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const cluster = require('cluster');
2
+ const { spawn } = require('child_process');
3
+ const path = require('path');
4
+ const fs = require('fs');
5
+ const os = require('os');
6
+ const express = require('express');
7
+ const app = express();
8
+
9
+ // Tetapkan port ke 7860
10
+ const PORT = 7860;
11
+
12
+ app.get('/', (req, res) => {
13
+ res.setHeader('Content-Type', 'application/json');
14
+ const data = {
15
+ status: 'true',
16
+ message: 'Bot Successfully Activated!',
17
+ author: 'rizki'
18
+ };
19
+ const result = {
20
+ response: data
21
+ };
22
+ res.send(JSON.stringify(result, null, 2));
23
+ });
24
+
25
+ // Mulai server pada port 7860
26
+ app.listen(PORT, () => {
27
+ console.log('\x1b[33m%s\x1b[0m', `🌐 Server berjalan di port ${PORT}`);
28
+ });
29
+
30
+ let isRunning = false;
31
+
32
+ function start(file) {
33
+ if (isRunning) return;
34
+ isRunning = true;
35
+
36
+ const args = [path.join(__dirname, file), ...process.argv.slice(2)];
37
+ const p = spawn(process.argv[0], args, {
38
+ stdio: ["inherit", "inherit", "inherit", "ipc"],
39
+ });
40
+
41
+ p.on("message", (data) => {
42
+ console.log('\x1b[36m%s\x1b[0m', `🟢 RECEIVED ${data}`);
43
+ switch (data) {
44
+ case "reset":
45
+ p.kill();
46
+ isRunning = false;
47
+ start.apply(this, arguments);
48
+ break;
49
+ case "uptime":
50
+ p.send(process.uptime());
51
+ break;
52
+ }
53
+ });
54
+
55
+ p.on("exit", (code) => {
56
+ isRunning = false;
57
+ console.error('\x1b[31m%s\x1b[0m', `Exited with code: ${code}`);
58
+ start('main.js');
59
+
60
+ if (code === 0) return;
61
+
62
+ fs.watchFile(args[0], () => {
63
+ fs.unwatchFile(args[0]);
64
+ console.error('\x1b[31m%s\x1b[0m', `File ${args[0]} has been modified. Script will restart...`);
65
+ start("main.js");
66
+ });
67
+ });
68
+
69
+ p.on("error", (err) => {
70
+ console.error('\x1b[31m%s\x1b[0m', `Error: ${err}`);
71
+ p.kill();
72
+ isRunning = false;
73
+ console.error('\x1b[31m%s\x1b[0m', `Error occurred. Script will restart...`);
74
+ start("main.js");
75
+ });
76
+
77
+ const pluginsFolder = path.join(__dirname, "plugins");
78
+
79
+ fs.readdir(pluginsFolder, (err, files) => {
80
+ if (err) {
81
+ console.error('\x1b[31m%s\x1b[0m', `Error reading plugins folder: ${err}`);
82
+ return;
83
+ }
84
+ console.log('\x1b[33m%s\x1b[0m', `🟡 Found ${files.length} plugins in folder ${pluginsFolder}`);
85
+ try {
86
+ require.resolve('@adiwajshing/baileys');
87
+ console.log('\x1b[33m%s\x1b[0m', `🟡 Baileys library version ${require('@adiwajshing/baileys/package.json').version} is installed`);
88
+ } catch (e) {
89
+ console.error('\x1b[31m%s\x1b[0m', `❌ Baileys library is not installed`);
90
+ }
91
+ });
92
+
93
+ console.log(`🖥️ \x1b[33m${os.type()}\x1b[0m, \x1b[33m${os.release()}\x1b[0m - \x1b[33m${os.arch()}\x1b[0m`);
94
+ const ramInGB = os.totalmem() / (1024 * 1024 * 1024);
95
+ console.log(`💾 \x1b[33mTotal RAM: ${ramInGB.toFixed(2)} GB\x1b[0m`);
96
+ const freeRamInGB = os.freemem() / (1024 * 1024 * 1024);
97
+ console.log(`💽 \x1b[33mFree RAM: ${freeRamInGB.toFixed(2)} GB\x1b[0m`);
98
+ console.log('\x1b[33m%s\x1b[0m', `📃 Script by BOTCAHX`);
99
+
100
+ setInterval(() => {}, 1000);
101
+ }
102
+
103
+ start("main.js");
104
+
105
+ const tmpDir = './tmp';
106
+ if (!fs.existsSync(tmpDir)) {
107
+ fs.mkdirSync(tmpDir);
108
+ console.log('\x1b[33m%s\x1b[0m', `📁 Created directory ${tmpDir}`);
109
+ }
110
+
111
+ process.on('unhandledRejection', (reason) => {
112
+ console.error('\x1b[31m%s\x1b[0m', `Unhandled promise rejection: ${reason}`);
113
+ console.error('\x1b[31m%s\x1b[0m', 'Unhandled promise rejection. Script will restart...');
114
+ start('main.js');
115
+ });
116
+
117
+ process.on('exit', (code) => {
118
+ console.error(`Exited with code: ${code}`);
119
+ console.error('Script will restart...');
120
+ start('main.js');
121
+ });
lib/cloudDBAdapter.js ADDED
@@ -0,0 +1,58 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const got = require('got')
2
+
3
+ const stringify = obj => JSON.stringify(obj, null, 2)
4
+ const parse = str => JSON.parse(str, (_, v) => {
5
+ if (
6
+ v !== null &&
7
+ typeof v === 'object' &&
8
+ 'type' in v &&
9
+ v.type === 'Buffer' &&
10
+ 'data' in v &&
11
+ Array.isArray(v.data)) {
12
+ return Buffer.from(v.data)
13
+ }
14
+ return v
15
+ })
16
+ class CloudDBAdapter {
17
+ constructor(url, {
18
+ serialize = stringify,
19
+ deserialize = parse,
20
+ fetchOptions = {}
21
+ } = {}) {
22
+ this.url = url
23
+ this.serialize = serialize
24
+ this.deserialize = deserialize
25
+ this.fetchOptions = fetchOptions
26
+ }
27
+
28
+ async read() {
29
+ try {
30
+ let res = await got(this.url, {
31
+ method: 'GET',
32
+ headers: {
33
+ 'Accept': 'application/json;q=0.9,text/plain'
34
+ },
35
+ ...this.fetchOptions
36
+ })
37
+ if (res.statusCode !== 200) throw res.statusMessage
38
+ return this.deserialize(res.body)
39
+ } catch (e) {
40
+ return null
41
+ }
42
+ }
43
+
44
+ async write(obj) {
45
+ let res = await got(this.url, {
46
+ method: 'POST',
47
+ headers: {
48
+ 'Content-Type': 'application/json'
49
+ },
50
+ ...this.fetchOptions,
51
+ body: this.serialize(obj)
52
+ })
53
+ if (res.statusCode !== 200) throw res.statusMessage
54
+ return res.body
55
+ }
56
+ }
57
+
58
+ module.exports = CloudDBAdapter
lib/cluster.js ADDED
@@ -0,0 +1,36 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const cluster = require('cluster')
2
+ const os = require('os')
3
+ const path = require('path')
4
+ const { connectionOptions } = require('../main')
5
+ const { makeWASocket } = require('./simple')
6
+
7
+ var conn
8
+ module.exports = {
9
+ Cluster() {
10
+ if (cluster.isMaster || !cluster.isWorker) {
11
+ if (!os.cpus().length <= 1) throw new Error(`Requires at least 1 cores, but you only have ${os.cpus().length} cores`)
12
+ cluster.setupMaster({
13
+ exec: path.join(__dirname, './cluster.js')
14
+ })
15
+ // for (let i = 0; i < 3; i++)
16
+ cluster.fork()
17
+ console.log(cluster.workers)
18
+ } else {
19
+ // console.log(cluster.workers)
20
+ // if (cluster.worker.id == 1) this.baileys()
21
+ }
22
+ },
23
+ baileys() {
24
+ conn = makeWASocket(connectionOptions)
25
+ for (let event of Object.keys(conn.ev._events)) {
26
+ conn.ev.on(event, (...updates) => {
27
+ event, updates
28
+ })
29
+ }
30
+ },
31
+ convert() {
32
+
33
+ }
34
+ }
35
+
36
+ if (cluster.isWorker) module.exports.Cluster()
lib/color.js ADDED
@@ -0,0 +1,14 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const chalk = require('chalk')
2
+
3
+ const color = (text, color) => {
4
+ return !color ? chalk.green(text) : chalk.keyword(color)(text)
5
+ }
6
+
7
+ const bgcolor = (text, bgcolor) => {
8
+ return !bgcolor ? chalk.green(text) : chalk.bgKeyword(bgcolor)(text)
9
+ }
10
+
11
+ module.exports = {
12
+ color,
13
+ bgcolor
14
+ }
lib/converter.js ADDED
@@ -0,0 +1,84 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const fs = require('fs')
2
+ const path = require('path')
3
+ const { spawn } = require('child_process')
4
+
5
+ function ffmpeg(buffer, args = [], ext = '', ext2 = '') {
6
+ return new Promise(async (resolve, reject) => {
7
+ try {
8
+ let tmp = path.join(__dirname, '../tmp', + new Date + '.' + ext)
9
+ let out = tmp + '.' + ext2
10
+ await fs.promises.writeFile(tmp, buffer)
11
+ spawn('ffmpeg', [
12
+ '-y',
13
+ '-i', tmp,
14
+ ...args,
15
+ out
16
+ ])
17
+ .on('error', reject)
18
+ .on('close', async (code) => {
19
+ try {
20
+ await fs.promises.unlink(tmp)
21
+ if (code !== 0) return reject(code)
22
+ resolve({ data: await fs.promises.readFile(out), filename: out })
23
+ // await fs.promises.unlink(out)
24
+ } catch (e) {
25
+ reject(e)
26
+ }
27
+ })
28
+ } catch (e) {
29
+ reject(e)
30
+ }
31
+ })
32
+ }
33
+
34
+ /**
35
+ * Convert Audio to Playable WhatsApp Audio
36
+ * @param {Buffer} buffer Audio Buffer
37
+ * @param {String} ext File Extension
38
+ */
39
+ function toPTT(buffer, ext) {
40
+ return ffmpeg(buffer, [
41
+ '-vn',
42
+ '-c:a', 'libopus',
43
+ '-b:a', '128k',
44
+ '-vbr', 'on',
45
+ ], ext, 'ogg')
46
+ }
47
+
48
+ /**
49
+ * Convert Audio to Playable WhatsApp PTT
50
+ * @param {Buffer} buffer Audio Buffer
51
+ * @param {String} ext File Extension
52
+ */
53
+ function toAudio(buffer, ext) {
54
+ return ffmpeg(buffer, [
55
+ '-vn',
56
+ '-c:a', 'libopus',
57
+ '-b:a', '128k',
58
+ '-vbr', 'on',
59
+ '-compression_level', '10'
60
+ ], ext, 'opus')
61
+ }
62
+
63
+ /**
64
+ * Convert Audio to Playable WhatsApp Video
65
+ * @param {Buffer} buffer Video Buffer
66
+ * @param {String} ext File Extension
67
+ */
68
+ function toVideo(buffer, ext) {
69
+ return ffmpeg(buffer, [
70
+ '-c:v', 'libx264',
71
+ '-c:a', 'aac',
72
+ '-ab', '128k',
73
+ '-ar', '44100',
74
+ '-crf', '32',
75
+ '-preset', 'slow'
76
+ ], ext, 'mp4')
77
+ }
78
+
79
+ module.exports = {
80
+ toAudio,
81
+ toPTT,
82
+ toVideo,
83
+ ffmpeg,
84
+ }
lib/database.js ADDED
@@ -0,0 +1,71 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const path = require('path')
2
+ const _fs = require('fs')
3
+ const { promises: fs } = _fs
4
+
5
+ class Database {
6
+ /**
7
+ * Create new Database
8
+ * @param {String} filepath Path to specified json database
9
+ * @param {...any} args JSON.stringify arguments
10
+ */
11
+ constructor(filepath, ...args) {
12
+ this.file = path.resolve(filepath)
13
+ this.logger = console
14
+
15
+ this._load()
16
+
17
+ this._jsonargs = args
18
+ this._state = false
19
+ this._queue = []
20
+ this._interval = setInterval(async () => {
21
+ if (!this._state && this._queue && this._queue[0]) {
22
+ this._state = true
23
+ await this[this._queue.shift()]().catch(this.logger.error)
24
+ this._state = false
25
+ }
26
+ }, 1000)
27
+
28
+ }
29
+
30
+ get data() {
31
+ return this._data
32
+ }
33
+
34
+ set data(value) {
35
+ this._data = value
36
+ this.save()
37
+ }
38
+
39
+ /**
40
+ * Queue Load
41
+ */
42
+ load() {
43
+ this._queue.push('_load')
44
+ }
45
+
46
+ /**
47
+ * Queue Save
48
+ */
49
+ save() {
50
+ this._queue.push('_save')
51
+ }
52
+
53
+ _load() {
54
+ try {
55
+ return this._data = _fs.existsSync(this.file) ? JSON.parse(_fs.readFileSync(this.file)) : {}
56
+ } catch (e) {
57
+ this.logger.error(e)
58
+ return this._data = {}
59
+ }
60
+ }
61
+
62
+ async _save() {
63
+ let dirname = path.dirname(this.file)
64
+ if (!_fs.existsSync(dirname)) await fs.mkdir(dirname, { recursive: true })
65
+ await fs.writeFile(this.file, JSON.stringify(this._data, ...this._jsonargs))
66
+ return this.file
67
+ }
68
+ }
69
+
70
+ module.exports = Database
71
+
lib/exif.js ADDED
@@ -0,0 +1,116 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const fs = require('fs')
2
+ const { tmpdir } = require("os")
3
+ const Crypto = require("crypto")
4
+ const ff = require('fluent-ffmpeg')
5
+ const webp = require("node-webpmux")
6
+ const path = require("path")
7
+
8
+
9
+ async function imageToWebp (media) {
10
+
11
+ const tmpFileOut = path.join(tmpdir(), `${Crypto.randomBytes(6).readUIntLE(0, 6).toString(36)}.webp`)
12
+ const tmpFileIn = path.join(tmpdir(), `${Crypto.randomBytes(6).readUIntLE(0, 6).toString(36)}.jpg`)
13
+
14
+ fs.writeFileSync(tmpFileIn, media)
15
+
16
+ await new Promise((resolve, reject) => {
17
+ ff(tmpFileIn)
18
+ .on("error", reject)
19
+ .on("end", () => resolve(true))
20
+ .addOutputOptions([
21
+ "-vcodec",
22
+ "libwebp",
23
+ "-vf",
24
+ "scale='min(320,iw)':min'(320,ih)':force_original_aspect_ratio=decrease,fps=15, pad=320:320:-1:-1:color=white@0.0, split [a][b]; [a] palettegen=reserve_transparent=on:transparency_color=ffffff [p]; [b][p] paletteuse"
25
+ ])
26
+ .toFormat("webp")
27
+ .save(tmpFileOut)
28
+ })
29
+
30
+ const buff = fs.readFileSync(tmpFileOut)
31
+ fs.unlinkSync(tmpFileOut)
32
+ fs.unlinkSync(tmpFileIn)
33
+ return buff
34
+ }
35
+
36
+ async function videoToWebp (media) {
37
+
38
+ const tmpFileOut = path.join(tmpdir(), `${Crypto.randomBytes(6).readUIntLE(0, 6).toString(36)}.webp`)
39
+ const tmpFileIn = path.join(tmpdir(), `${Crypto.randomBytes(6).readUIntLE(0, 6).toString(36)}.mp4`)
40
+
41
+ fs.writeFileSync(tmpFileIn, media)
42
+
43
+ await new Promise((resolve, reject) => {
44
+ ff(tmpFileIn)
45
+ .on("error", reject)
46
+ .on("end", () => resolve(true))
47
+ .addOutputOptions([
48
+ "-vcodec",
49
+ "libwebp",
50
+ "-vf",
51
+ "scale='min(320,iw)':min'(320,ih)':force_original_aspect_ratio=decrease,fps=15, pad=320:320:-1:-1:color=white@0.0, split [a][b]; [a] palettegen=reserve_transparent=on:transparency_color=ffffff [p]; [b][p] paletteuse",
52
+ "-loop",
53
+ "0",
54
+ "-ss",
55
+ "00:00:00",
56
+ "-t",
57
+ "00:00:06",
58
+ "-preset",
59
+ "default",
60
+ "-an",
61
+ "-vsync",
62
+ "0"
63
+ ])
64
+ .toFormat("webp")
65
+ .save(tmpFileOut)
66
+ })
67
+
68
+ const buff = fs.readFileSync(tmpFileOut)
69
+ fs.unlinkSync(tmpFileOut)
70
+ fs.unlinkSync(tmpFileIn)
71
+ return buff
72
+ }
73
+
74
+ async function writeExifImg (media, metadata) {
75
+ let wMedia = await imageToWebp(media)
76
+ const tmpFileIn = path.join(tmpdir(), `${Crypto.randomBytes(6).readUIntLE(0, 6).toString(36)}.webp`)
77
+ const tmpFileOut = path.join(tmpdir(), `${Crypto.randomBytes(6).readUIntLE(0, 6).toString(36)}.webp`)
78
+ fs.writeFileSync(tmpFileIn, wMedia)
79
+
80
+ if (metadata.packname || metadata.author) {
81
+ const img = new webp.Image()
82
+ const json = { "sticker-pack-id": `https://github.com/BOTCAHX/RTXZY-MD`, "sticker-pack-name": metadata.packname, "sticker-pack-publisher": metadata.author, "emojis": metadata.categories ? metadata.categories : [""] }
83
+ const exifAttr = Buffer.from([0x49, 0x49, 0x2A, 0x00, 0x08, 0x00, 0x00, 0x00, 0x01, 0x00, 0x41, 0x57, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x16, 0x00, 0x00, 0x00])
84
+ const jsonBuff = Buffer.from(JSON.stringify(json), "utf-8")
85
+ const exif = Buffer.concat([exifAttr, jsonBuff])
86
+ exif.writeUIntLE(jsonBuff.length, 14, 4)
87
+ await img.load(tmpFileIn)
88
+ fs.unlinkSync(tmpFileIn)
89
+ img.exif = exif
90
+ await img.save(tmpFileOut)
91
+ return tmpFileOut
92
+ }
93
+ }
94
+
95
+ async function writeExifVid (media, metadata) {
96
+ let wMedia = await videoToWebp(media)
97
+ const tmpFileIn = path.join(tmpdir(), `${Crypto.randomBytes(6).readUIntLE(0, 6).toString(36)}.webp`)
98
+ const tmpFileOut = path.join(tmpdir(), `${Crypto.randomBytes(6).readUIntLE(0, 6).toString(36)}.webp`)
99
+ fs.writeFileSync(tmpFileIn, wMedia)
100
+
101
+ if (metadata.packname || metadata.author) {
102
+ const img = new webp.Image()
103
+ const json = { "sticker-pack-id": `https://github.com/BOTCAHX/RTXZY-MD`, "sticker-pack-name": metadata.packname, "sticker-pack-publisher": metadata.author, "emojis": metadata.categories ? metadata.categories : [""] }
104
+ const exifAttr = Buffer.from([0x49, 0x49, 0x2A, 0x00, 0x08, 0x00, 0x00, 0x00, 0x01, 0x00, 0x41, 0x57, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x16, 0x00, 0x00, 0x00])
105
+ const jsonBuff = Buffer.from(JSON.stringify(json), "utf-8")
106
+ const exif = Buffer.concat([exifAttr, jsonBuff])
107
+ exif.writeUIntLE(jsonBuff.length, 14, 4)
108
+ await img.load(tmpFileIn)
109
+ fs.unlinkSync(tmpFileIn)
110
+ img.exif = exif
111
+ await img.save(tmpFileOut)
112
+ return tmpFileOut
113
+ }
114
+ }
115
+
116
+ module.exports = { imageToWebp, videoToWebp, writeExifImg, writeExifVid }
lib/functions.js ADDED
@@ -0,0 +1,149 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const fetch = require('node-fetch')
2
+ const axios = require('axios')
3
+ const cfonts = require('cfonts')
4
+ const spin = require('spinnies')
5
+ const Crypto = require('crypto')
6
+
7
+ const wait = async (media) => new Promise(async (resolve, reject) => {
8
+ const attachmentData = `data:image/jpeg;base64,${media.toString('base64')}`
9
+ const response = await fetch("https://trace.moe/api/search",{method: "POST",body: JSON.stringify({ image: attachmentData }),headers: { "Content-Type": "application/json" }});
10
+ if (!response.ok) reject(`Gambar tidak ditemukan!`);
11
+ const result = await response.json()
12
+ try {
13
+ const { is_adult, title, title_chinese, title_romaji, title_english, episode, season, similarity, filename, at, tokenthumb, anilist_id } = result.docs[0]
14
+ let belief = () => similarity < 0.89 ? "Saya memiliki keyakinan rendah dalam hal ini : " : ""
15
+ let ecch = () => is_adult ? "Iya" : "Tidak"
16
+ resolve({video: await getBuffer(`https://media.trace.moe/video/${anilist_id}/${encodeURIComponent(filename)}?t=${at}&token=${tokenthumb}`), teks: `${belief()}
17
+ ~> Ecchi : *${ecch()}*
18
+ ~> Judul Jepang : *${title}*
19
+ ~> Ejaan Judul : *${title_romaji}*
20
+ ~> Judul Inggris : *${title_english}*
21
+ ~> Episode : *${episode}*
22
+ ~> Season : *${season}*`});
23
+ } catch (e) {
24
+ console.log(e)
25
+ reject(`Saya tidak tau ini anime apa`)
26
+ }
27
+ })
28
+
29
+ const simih = async (text) => {
30
+ try {
31
+ const sami = await fetch(`https://simsumi.herokuapp.com/api?text=${text}`, {method: 'GET'})
32
+ const res = await sami.json()
33
+ return res.success
34
+ } catch {
35
+ return 'Simi ga tau apa yang anda ngomong, bahasa alien yah kak?'
36
+ }
37
+ }
38
+
39
+ const h2k = (number) => {
40
+ var SI_POSTFIXES = ["", " K", " M", " G", " T", " P", " E"]
41
+ var tier = Math.log10(Math.abs(number)) / 3 | 0
42
+ if(tier == 0) return number
43
+ var postfix = SI_POSTFIXES[tier]
44
+ var scale = Math.pow(10, tier * 3)
45
+ var scaled = number / scale
46
+ var formatted = scaled.toFixed(1) + ''
47
+ if (/\.0$/.test(formatted))
48
+ formatted = formatted.substr(0, formatted.length - 2)
49
+ return formatted + postfix
50
+ }
51
+
52
+ const getBuffer = async (url, options) => {
53
+ try {
54
+ options ? options : {}
55
+ const res = await axios({
56
+ method: "get",
57
+ url,
58
+ headers: {
59
+ 'DNT': 1,
60
+ 'Upgrade-Insecure-Request': 1
61
+ },
62
+ ...options,
63
+ responseType: 'arraybuffer'
64
+ })
65
+ return res.data
66
+ } catch (e) {
67
+ console.log(`Error : ${e}`)
68
+ }
69
+ }
70
+
71
+ const randomBytes = (length) => {
72
+ return Crypto.randomBytes(length)
73
+ }
74
+
75
+ const generateMessageID = () => {
76
+ return randomBytes(10).toString('hex').toUpperCase()
77
+ }
78
+
79
+ const getGroupAdmins = (participants) => {
80
+ admins = []
81
+ for (let i of participants) {
82
+ i.isAdmin ? admins.push(i.jid) : ''
83
+ }
84
+ return admins
85
+ }
86
+
87
+ const getRandom = (ext) => {
88
+ return `${Math.floor(Math.random() * 10000)}${ext}`
89
+ }
90
+
91
+ function pickRandom(list) {
92
+ return list[Math.floor(Math.random() * list.length)]
93
+ }
94
+
95
+ const spinner = {
96
+ "interval": 120,
97
+ "frames": [
98
+ "🕐",
99
+ "🕑",
100
+ "🕒",
101
+ "🕓",
102
+ "🕔",
103
+ "🕕",
104
+ "🕖",
105
+ "🕗",
106
+ "🕘",
107
+ "🕙",
108
+ "🕚",
109
+ "🕛"
110
+ ]}
111
+
112
+ let globalSpinner;
113
+
114
+
115
+ const getGlobalSpinner = (disableSpins = false) => {
116
+ if(!globalSpinner) globalSpinner = new spin({ color: 'blue', succeedColor: 'green', spinner, disableSpins});
117
+ return globalSpinner;
118
+ }
119
+
120
+ spins = getGlobalSpinner(false)
121
+
122
+ const start = (id, text) => {
123
+ spins.add(id, {text: text})
124
+ /*setTimeout(() => {
125
+ spins.succeed('load-spin', {text: 'Suksess'})
126
+ }, Number(wait) * 1000)*/
127
+ }
128
+ const info = (id, text) => {
129
+ spins.update(id, {text: text})
130
+ }
131
+ const success = (id, text) => {
132
+ spins.succeed(id, {text: text})
133
+
134
+ }
135
+
136
+ const close = (id, text) => {
137
+ spins.fail(id, {text: text})
138
+ }
139
+
140
+ const banner = cfonts.render(('LOADING...'), {
141
+ font: 'chrome',
142
+ color: 'candy',
143
+ align: 'center',
144
+ gradient: ["red","yellow"],
145
+ lineHeight: 3
146
+ });
147
+
148
+
149
+ module.exports = { wait, simih, getBuffer, h2k, generateMessageID, getGroupAdmins, getRandom, start, info, success, banner, close, pickRandom }
lib/gdrive.js ADDED
@@ -0,0 +1,75 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ let path = require('path')
2
+ let fs = require('fs').promises
3
+ let { promisify } = require('util')
4
+ let { google } = require('googleapis')
5
+
6
+
7
+ // If modifying these scopes, delete token.json.
8
+ const SCOPES = ['https://www.googleapis.com/auth/drive.metadata.readonly']
9
+ // The file token.json stores the user's access and refresh tokens, and is
10
+ // created automatically when the authorization flow completes for the first
11
+ // time.
12
+ const TOKEN_PATH = path.join(__dirname, '..', 'token.json')
13
+ let
14
+
15
+ class GoogleAuth extends EventEmitter {
16
+ constructor() {
17
+ super()
18
+ }
19
+
20
+ async authorize(credentials) {
21
+ let token
22
+ const { client_secret, client_id } = credentials
23
+ const oAuth2Client = new google.auth.OAuth2(client_id, client_secret, `http://localhost:${port}`)
24
+ try {
25
+ token = JSON.parse(await fs.readFile(TOKEN_PATH))
26
+ } catch (e) {
27
+ const authUrl = oAuth2Client.generateAuthUrl({
28
+ access_type: 'offline',
29
+ scope: SCOPES
30
+ })
31
+ this.emit('auth', authUrl)
32
+ let code = await promisify(this.once).bind(this)('token')
33
+ token = await oAuth2Client.getToken(code)
34
+ await fs.writeFile(TOKEN_PATH, JSON.stringify(token))
35
+ } finally {
36
+ await oAuth2Client.setCredentials(token)
37
+ }
38
+ }
39
+
40
+ token(code) {
41
+ this.emit('token', code)
42
+ }
43
+ }
44
+
45
+ class GoogleDrive extends GoogleAuth {
46
+ constructor() {
47
+ super()
48
+ this.path = '/drive/api'
49
+ }
50
+
51
+ async getFolderID(path) {
52
+
53
+ }
54
+
55
+ async infoFile(path) {
56
+
57
+ }
58
+
59
+ async folderList(path) {
60
+
61
+ }
62
+
63
+ async downloadFile(path) {
64
+
65
+ }
66
+
67
+ async uploadFile(path) {
68
+
69
+ }
70
+ }
71
+
72
+ module.exports = {
73
+ GoogleAuth,
74
+ GoogleDrive,
75
+ }
lib/levelling.js ADDED
@@ -0,0 +1,50 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ module.exports = {
2
+ /**
3
+ * Growth rate
4
+ * `2.576652002695681`
5
+ */
6
+ growth: Math.pow(Math.PI / Math.E, 1.618) * Math.E * .75,
7
+ /**
8
+ * get XP range at specified level
9
+ * @param {Number} level
10
+ * @param {Number} multiplier
11
+ */
12
+ xpRange(level, multiplier = global.multiplier || 1) {
13
+ if (level < 0) throw new TypeError('level cannot be negative value')
14
+ level = Math.floor(level)
15
+ let min = level === 0 ? 0 : Math.round(Math.pow(level, this.growth) * multiplier) + 1
16
+ let max = Math.round(Math.pow(++level, this.growth) * multiplier)
17
+ return {
18
+ min,
19
+ max,
20
+ xp: max - min
21
+ }
22
+ },
23
+ /**
24
+ * get level by xp
25
+ * @param {Number} xp
26
+ * @param {Number} multiplier
27
+ */
28
+ findLevel(xp, multiplier = global.multiplier || 1) {
29
+ if (xp === Infinity) return Infinity
30
+ if (isNaN(xp)) return NaN
31
+ if (xp <= 0) return -1
32
+ let level = 0
33
+ do level++
34
+ while (this.xpRange(level, multiplier).min <= xp)
35
+ return --level
36
+ },
37
+ /**
38
+ * is able to level up?
39
+ * @param {Number} level
40
+ * @param {Number} xp
41
+ * @param {Number} multiplier
42
+ */
43
+ canLevelUp(level, xp, multiplier = global.multiplier || 1) {
44
+ if (level < 0) return false
45
+ if (xp === Infinity) return true
46
+ if (isNaN(xp)) return false
47
+ if (xp <= 0) return false
48
+ return level < this.findLevel(xp, multiplier)
49
+ }
50
+ }
lib/logs.js ADDED
@@ -0,0 +1,19 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ let stdouts = []
2
+ module.exports = (maxLength = 200) => {
3
+ let oldWrite = process.stdout.write.bind(process.stdout)
4
+ module.exports.disable = () => {
5
+ module.exports.isModified = false
6
+ return process.stdout.write = oldWrite
7
+ }
8
+ process.stdout.write = (chunk, encoding, callback) => {
9
+ stdouts.push(Buffer.from(chunk, encoding))
10
+ oldWrite(chunk, encoding, callback)
11
+ if (stdouts.length > maxLength) stdouts.shift()
12
+ }
13
+ module.exports.isModified = true
14
+ return module.exports
15
+ }
16
+
17
+ module.exports.isModified = false
18
+ module.exports.logs = () => Buffer.concat(stdouts)
19
+
lib/lowdb/Low.d.ts ADDED
@@ -0,0 +1,11 @@
 
 
 
 
 
 
 
 
 
 
 
 
1
+ export interface Adapter<T> {
2
+ read: () => Promise<T | null>;
3
+ write: (data: T) => Promise<void>;
4
+ }
5
+ export declare class Low<T = unknown> {
6
+ adapter: Adapter<T>;
7
+ data: T | null;
8
+ constructor(adapter: Adapter<T>);
9
+ read(): Promise<void>;
10
+ write(): Promise<void>;
11
+ }
lib/lowdb/Low.js ADDED
@@ -0,0 +1,21 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const { MissingAdapterError } = require('./MissingAdapterError.js');
2
+ class Low {
3
+ constructor(adapter) {
4
+ this.data = null;
5
+ if (adapter) {
6
+ this.adapter = adapter;
7
+ }
8
+ else {
9
+ throw new MissingAdapterError();
10
+ }
11
+ }
12
+ async read() {
13
+ this.data = await this.adapter.read();
14
+ }
15
+ async write() {
16
+ if (this.data) {
17
+ await this.adapter.write(this.data);
18
+ }
19
+ }
20
+ }
21
+ module.exports = { Low };
lib/lowdb/LowSync.d.ts ADDED
@@ -0,0 +1,11 @@
 
 
 
 
 
 
 
 
 
 
 
 
1
+ export interface SyncAdapter<T> {
2
+ read: () => T | null;
3
+ write: (data: T) => void;
4
+ }
5
+ export declare class LowSync<T = unknown> {
6
+ adapter: SyncAdapter<T>;
7
+ data: T | null;
8
+ constructor(adapter: SyncAdapter<T>);
9
+ read(): void;
10
+ write(): void;
11
+ }
lib/lowdb/LowSync.js ADDED
@@ -0,0 +1,21 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const { MissingAdapterError } = require('./MissingAdapterError.js');
2
+ class LowSync {
3
+ constructor(adapter) {
4
+ this.data = null;
5
+ if (adapter) {
6
+ this.adapter = adapter;
7
+ }
8
+ else {
9
+ throw new MissingAdapterError();
10
+ }
11
+ }
12
+ read() {
13
+ this.data = this.adapter.read();
14
+ }
15
+ write() {
16
+ if (this.data !== null) {
17
+ this.adapter.write(this.data);
18
+ }
19
+ }
20
+ }
21
+ module.exports = { LowSync };
lib/lowdb/MissingAdapterError.d.ts ADDED
@@ -0,0 +1,3 @@
 
 
 
 
1
+ export declare class MissingAdapterError extends Error {
2
+ constructor();
3
+ }
lib/lowdb/MissingAdapterError.js ADDED
@@ -0,0 +1,7 @@
 
 
 
 
 
 
 
 
1
+ class MissingAdapterError extends Error {
2
+ constructor() {
3
+ super();
4
+ this.message = 'Missing Adapter';
5
+ }
6
+ }
7
+ module.exports = { MissingAdapterError };
lib/lowdb/adapters/JSONFile.d.ts ADDED
@@ -0,0 +1,7 @@
 
 
 
 
 
 
 
 
1
+ import { Adapter } from '../Low.js';
2
+ export declare class JSONFile<T> implements Adapter<T> {
3
+ private adapter;
4
+ constructor(filename: string);
5
+ read(): Promise<T | null>;
6
+ write(obj: T): Promise<void>;
7
+ }
lib/lowdb/adapters/JSONFile.js ADDED
@@ -0,0 +1,19 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const { TextFile } = require('./TextFile.js');
2
+ class JSONFile {
3
+ constructor(filename) {
4
+ this.adapter = new TextFile(filename);
5
+ }
6
+ async read() {
7
+ const data = await this.adapter.read();
8
+ if (data === null) {
9
+ return null;
10
+ }
11
+ else {
12
+ return JSON.parse(data);
13
+ }
14
+ }
15
+ write(obj) {
16
+ return this.adapter.write(JSON.stringify(obj, null, 2));
17
+ }
18
+ }
19
+ module.exports = { JSONFile };
lib/lowdb/adapters/JSONFileSync.d.ts ADDED
@@ -0,0 +1,7 @@
 
 
 
 
 
 
 
 
1
+ import { SyncAdapter } from '../LowSync.js';
2
+ export declare class JSONFileSync<T> implements SyncAdapter<T> {
3
+ private adapter;
4
+ constructor(filename: string);
5
+ read(): T | null;
6
+ write(obj: T): void;
7
+ }
lib/lowdb/adapters/JSONFileSync.js ADDED
@@ -0,0 +1,19 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const { TextFileSync } = require('./TextFileSync.js');
2
+ class JSONFileSync {
3
+ constructor(filename) {
4
+ this.adapter = new TextFileSync(filename);
5
+ }
6
+ read() {
7
+ const data = this.adapter.read();
8
+ if (data === null) {
9
+ return null;
10
+ }
11
+ else {
12
+ return JSON.parse(data);
13
+ }
14
+ }
15
+ write(obj) {
16
+ this.adapter.write(JSON.stringify(obj, null, 2));
17
+ }
18
+ }
19
+ module.exports = { JSONFileSync };
lib/lowdb/adapters/LocalStorage.d.ts ADDED
@@ -0,0 +1,7 @@
 
 
 
 
 
 
 
 
1
+ import { SyncAdapter } from '../LowSync.js';
2
+ export declare class LocalStorage<T> implements SyncAdapter<T> {
3
+ private key;
4
+ constructor(key: string);
5
+ read(): T | null;
6
+ write(obj: T): void;
7
+ }
lib/lowdb/adapters/LocalStorage.js ADDED
@@ -0,0 +1,16 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ class LocalStorage {
2
+ constructor(key) {
3
+ this.key = key;
4
+ }
5
+ read() {
6
+ const value = localStorage.getItem(this.key);
7
+ if (value === null) {
8
+ return null;
9
+ }
10
+ return JSON.parse(value);
11
+ }
12
+ write(obj) {
13
+ localStorage.setItem(this.key, JSON.stringify(obj));
14
+ }
15
+ }
16
+ module.exports = { LocalStorage };
lib/lowdb/adapters/Memory.d.ts ADDED
@@ -0,0 +1,6 @@
 
 
 
 
 
 
 
1
+ import { Adapter } from '../Low.js';
2
+ export declare class Memory<T> implements Adapter<T> {
3
+ private data;
4
+ read(): Promise<T | null>;
5
+ write(obj: T): Promise<void>;
6
+ }
lib/lowdb/adapters/Memory.js ADDED
@@ -0,0 +1,13 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ class Memory {
2
+ constructor() {
3
+ this.data = null;
4
+ }
5
+ read() {
6
+ return Promise.resolve(this.data);
7
+ }
8
+ write(obj) {
9
+ this.data = obj;
10
+ return Promise.resolve();
11
+ }
12
+ }
13
+ module.exports = { Memory };
lib/lowdb/adapters/MemorySync.d.ts ADDED
@@ -0,0 +1,6 @@
 
 
 
 
 
 
 
1
+ import { SyncAdapter } from '../LowSync.js';
2
+ export declare class MemorySync<T> implements SyncAdapter<T> {
3
+ private data;
4
+ read(): T | null;
5
+ write(obj: T): void;
6
+ }
lib/lowdb/adapters/MemorySync.js ADDED
@@ -0,0 +1,12 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ class MemorySync {
2
+ constructor() {
3
+ this.data = null;
4
+ }
5
+ read() {
6
+ return this.data || null;
7
+ }
8
+ write(obj) {
9
+ this.data = obj;
10
+ }
11
+ }
12
+ module.exports = { MemorySync };
lib/lowdb/adapters/TextFile.d.ts ADDED
@@ -0,0 +1,8 @@
 
 
 
 
 
 
 
 
 
1
+ import { Adapter } from '../Low.js';
2
+ export declare class TextFile implements Adapter<string> {
3
+ private filename;
4
+ private writer;
5
+ constructor(filename: string);
6
+ read(): Promise<string | null>;
7
+ write(str: string): Promise<void>;
8
+ }
lib/lowdb/adapters/TextFile.js ADDED
@@ -0,0 +1,25 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const fs = require('fs');
2
+ const { Writer } = require('steno');
3
+ class TextFile {
4
+ constructor(filename) {
5
+ this.filename = filename;
6
+ this.writer = new Writer(filename);
7
+ }
8
+ async read() {
9
+ let data;
10
+ try {
11
+ data = await fs.promises.readFile(this.filename, 'utf-8');
12
+ }
13
+ catch (e) {
14
+ if (e.code === 'ENOENT') {
15
+ return null;
16
+ }
17
+ throw e;
18
+ }
19
+ return data;
20
+ }
21
+ write(str) {
22
+ return this.writer.write(str);
23
+ }
24
+ }
25
+ module.exports = { TextFile };
lib/lowdb/adapters/TextFileSync.d.ts ADDED
@@ -0,0 +1,8 @@
 
 
 
 
 
 
 
 
 
1
+ import { SyncAdapter } from '../LowSync.js';
2
+ export declare class TextFileSync implements SyncAdapter<string> {
3
+ private tempFilename;
4
+ private filename;
5
+ constructor(filename: string);
6
+ read(): string | null;
7
+ write(str: string): void;
8
+ }
lib/lowdb/adapters/TextFileSync.js ADDED
@@ -0,0 +1,26 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const fs = require('fs');
2
+ const path = require('path');
3
+ class TextFileSync {
4
+ constructor(filename) {
5
+ this.filename = filename;
6
+ this.tempFilename = path.join(path.dirname(filename), `.${path.basename(filename)}.tmp`);
7
+ }
8
+ read() {
9
+ let data;
10
+ try {
11
+ data = fs.readFileSync(this.filename, 'utf-8');
12
+ }
13
+ catch (e) {
14
+ if (e.code === 'ENOENT') {
15
+ return null;
16
+ }
17
+ throw e;
18
+ }
19
+ return data;
20
+ }
21
+ write(str) {
22
+ fs.writeFileSync(this.tempFilename, str);
23
+ fs.renameSync(this.tempFilename, this.filename);
24
+ }
25
+ }
26
+ module.exports = { TextFileSync };
lib/lowdb/index.d.ts ADDED
@@ -0,0 +1,9 @@
 
 
 
 
 
 
 
 
 
 
1
+ export * from './adapters/JSONFile.js';
2
+ export * from './adapters/JSONFileSync.js';
3
+ export * from './adapters/LocalStorage.js';
4
+ export * from './adapters/Memory.js';
5
+ export * from './adapters/MemorySync.js';
6
+ export * from './adapters/TextFile.js';
7
+ export * from './adapters/TextFileSync.js';
8
+ export * from './Low.js';
9
+ export * from './LowSync.js';
lib/lowdb/index.js ADDED
@@ -0,0 +1,11 @@
 
 
 
 
 
 
 
 
 
 
 
 
1
+ module.exports = {
2
+ ...require('./adapters/JSONFile.js'),
3
+ ...require('./adapters/JSONFileSync.js'),
4
+ ...require('./adapters/LocalStorage.js'),
5
+ ...require('./adapters/Memory.js'),
6
+ ...require('./adapters/MemorySync.js'),
7
+ ...require('./adapters/TextFile.js'),
8
+ ...require('./adapters/TextFileSync.js'),
9
+ ...require('./Low.js'),
10
+ ...require('./LowSync.js'),
11
+ }
lib/mongoDB.js ADDED
@@ -0,0 +1,44 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const mongoose = require('mongoose')
2
+ const { Schema } = mongoose
3
+
4
+ module.exports = class mongoDB {
5
+ constructor(url, options = { useNewUrlParser: true, useUnifiedTopology: true }) {
6
+ this.url = url
7
+ this.data = this._data = this._schema = this._model = {}
8
+ this.db
9
+ this.options = options
10
+ }
11
+ async read() {
12
+ this.db = await mongoose.connect(this.url, { ...this.options })
13
+ this.connection = mongoose.connection
14
+ let schema = this._schema = new Schema({
15
+ data: {
16
+ type: Object,
17
+ required: true, //depends on whether the field is mandatory or not
18
+ default: {}
19
+ }
20
+ })
21
+ // this._model = mongoose.model('data', schema)
22
+ try { this._model = mongoose.model('data', schema) } catch { this._model = mongoose.model('data') }
23
+ this._data = await this._model.findOne({})
24
+ if (!this._data) {
25
+ this.data = {}
26
+ await this.write(this.data)
27
+ this._data = await this._model.findOne({})
28
+ } else this.data = this._data.data
29
+ return this.data
30
+ }
31
+
32
+
33
+ async write(data) {
34
+ if (!data) return data
35
+ if (!this._data) return (new this._model({ data })).save()
36
+ this._model.findById(this._data._id, (err, docs) => {
37
+ if (!err) {
38
+ if (!docs.data) docs.data = {}
39
+ docs.data = data
40
+ return docs.save()
41
+ }
42
+ })
43
+ }
44
+ }
lib/myfunc.js ADDED
@@ -0,0 +1,307 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ /**
2
+ * Create By Dika Ardnt.
3
+ * Contact Me on wa.me/6288292024190
4
+ * Follow https://github.com/DikaArdnt
5
+ */
6
+
7
+ const { proto } = require('@adiwajshing/baileys')
8
+ const chalk = require('chalk')
9
+ const fs = require('fs')
10
+ const Crypto = require('crypto')
11
+ const axios = require('axios')
12
+ const moment = require('moment-timezone')
13
+ const { sizeFormatter } = require('human-readable')
14
+ const util = require('util')
15
+ const jimp = require('jimp')
16
+ const { defaultMaxListeners } = require('stream')
17
+
18
+
19
+ const unixTimestampSeconds = (date = new Date()) => Math.floor(date.getTime() / 1000)
20
+
21
+ exports.unixTimestampSeconds = unixTimestampSeconds
22
+
23
+ exports.generateMessageTag = (epoch) => {
24
+ let tag = (0, exports.unixTimestampSeconds)().toString();
25
+ if (epoch)
26
+ tag += '.--' + epoch; // attach epoch if provided
27
+ return tag;
28
+ }
29
+
30
+ exports.processTime = (timestamp, now) => {
31
+ return moment.duration(now - moment(timestamp * 1000)).asSeconds()
32
+ }
33
+
34
+ exports.getRandom = (ext) => {
35
+ return `${Math.floor(Math.random() * 10000)}${ext}`
36
+ }
37
+
38
+ exports.getBuffer = async (url, options) => {
39
+ try {
40
+ options ? options : {}
41
+ const res = await axios({
42
+ method: "get",
43
+ url,
44
+ headers: {
45
+ 'DNT': 1,
46
+ 'Upgrade-Insecure-Request': 1
47
+ },
48
+ ...options,
49
+ responseType: 'arraybuffer'
50
+ })
51
+ return res.data
52
+ } catch (e) {
53
+ return err
54
+ }
55
+ }
56
+
57
+ exports.fetchJson = async (url, options) => {
58
+ try {
59
+ options ? options : {}
60
+ const res = await axios({
61
+ method: 'GET',
62
+ url: url,
63
+ headers: {
64
+ 'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/95.0.4638.69 Safari/537.36'
65
+ },
66
+ ...options
67
+ })
68
+ return res.data
69
+ } catch (err) {
70
+ return err
71
+ }
72
+ }
73
+
74
+ exports.runtime = function(seconds) {
75
+ seconds = Number(seconds);
76
+ var d = Math.floor(seconds / (3600 * 24));
77
+ var h = Math.floor(seconds % (3600 * 24) / 3600);
78
+ var m = Math.floor(seconds % 3600 / 60);
79
+ var s = Math.floor(seconds % 60);
80
+ var dDisplay = d > 0 ? d + (d == 1 ? " day, " : " days, ") : "";
81
+ var hDisplay = h > 0 ? h + (h == 1 ? " hour, " : " hours, ") : "";
82
+ var mDisplay = m > 0 ? m + (m == 1 ? " minute, " : " minutes, ") : "";
83
+ var sDisplay = s > 0 ? s + (s == 1 ? " second" : " seconds") : "";
84
+ return dDisplay + hDisplay + mDisplay + sDisplay;
85
+ }
86
+
87
+ exports.clockString = function(seconds) {
88
+ let h = isNaN(seconds) ? '--' : Math.floor(seconds % (3600 * 24) / 3600)
89
+ let m = isNaN(seconds) ? '--' : Math.floor(seconds % 3600 / 60)
90
+ let s = isNaN(seconds) ? '--' : Math.floor(seconds % 60)
91
+ return [h, m, s].map(v => v.toString().padStart(2, 0)).join(':')
92
+ }
93
+
94
+ exports.sleep = async (ms) => {
95
+ return new Promise(resolve => setTimeout(resolve, ms));
96
+ }
97
+
98
+ exports.isUrl = (url) => {
99
+ return url.match(new RegExp(/https?:\/\/(www\.)?[-a-zA-Z0-9@:%._+~#=]{1,256}\.[a-zA-Z0-9()]{1,6}\b([-a-zA-Z0-9()@:%_+.~#?&/=]*)/, 'gi'))
100
+ }
101
+
102
+ exports.getTime = (format, date) => {
103
+ if (date) {
104
+ return moment(date).locale('id').format(format)
105
+ } else {
106
+ return moment.tz('Asia/Jakarta').locale('id').format(format)
107
+ }
108
+ }
109
+
110
+ exports.formatDate = (n, locale = 'id') => {
111
+ let d = new Date(n)
112
+ return d.toLocaleDateString(locale, {
113
+ weekday: 'long',
114
+ day: 'numeric',
115
+ month: 'long',
116
+ year: 'numeric',
117
+ hour: 'numeric',
118
+ minute: 'numeric',
119
+ second: 'numeric'
120
+ })
121
+ }
122
+
123
+ exports.tanggal = (numer) => {
124
+ myMonths = ["Januari","Februari","Maret","April","Mei","Juni","Juli","Agustus","September","Oktober","November","Desember"];
125
+ myDays = ['Minggu','Senin','Selasa','Rabu','Kamis','Jum’at','Sabtu'];
126
+ var tgl = new Date(numer);
127
+ var day = tgl.getDate()
128
+ bulan = tgl.getMonth()
129
+ var thisDay = tgl.getDay(),
130
+ thisDay = myDays[thisDay];
131
+ var yy = tgl.getYear()
132
+ var year = (yy < 1000) ? yy + 1900 : yy;
133
+ const time = moment.tz('Asia/Jakarta').format('DD/MM HH:mm:ss')
134
+ let d = new Date
135
+ let locale = 'id'
136
+ let gmt = new Date(0).getTime() - new Date('1 January 1970').getTime()
137
+ let weton = ['Pahing', 'Pon','Wage','Kliwon','Legi'][Math.floor(((d * 1) + gmt) / 84600000) % 5]
138
+
139
+ return`${thisDay}, ${day} - ${myMonths[bulan]} - ${year}`
140
+ }
141
+
142
+ exports.formatp = sizeFormatter({
143
+ std: 'JEDEC', //'SI' = default | 'IEC' | 'JEDEC'
144
+ decimalPlaces: 2,
145
+ keepTrailingZeroes: false,
146
+ render: (literal, symbol) => `${literal} ${symbol}B`,
147
+ })
148
+
149
+ exports.jsonformat = (string) => {
150
+ return JSON.stringify(string, null, 2)
151
+ }
152
+
153
+ function delay(ms) {
154
+ return new Promise((resolve, reject) => setTimeout(resolve, ms))
155
+ }
156
+
157
+ function format(...args) {
158
+ return util.format(...args)
159
+ }
160
+
161
+ exports.logic = (check, inp, out) => {
162
+ if (inp.length !== out.length) throw new Error('Input and Output must have same length')
163
+ for (let i in inp)
164
+ if (util.isDeepStrictEqual(check, inp[i])) return out[i]
165
+ return null
166
+ }
167
+
168
+ exports.generateProfilePicture = async (buffer) => {
169
+ const jimp = await jimp_1.read(buffer)
170
+ const min = jimp.getWidth()
171
+ const max = jimp.getHeight()
172
+ const cropped = jimp.crop(0, 0, min, max)
173
+ return {
174
+ img: await cropped.scaleToFit(720, 720).getBufferAsync(jimp_1.MIME_JPEG),
175
+ preview: await cropped.scaleToFit(720, 720).getBufferAsync(jimp_1.MIME_JPEG)
176
+ }
177
+ }
178
+
179
+ exports.parseMention = (text = '') => {
180
+ return [...text.matchAll(/@([0-9]{5,16}|0)/g)].map(v => v[1] + '@s.whatsapp.net')
181
+ }
182
+
183
+ exports.getGroupAdmins = (participantes) => {
184
+ var admins = []
185
+ for (let i of participantes) {
186
+ i.admin === "admin" ? admins.push(i.id) : ''
187
+ }
188
+ return admins
189
+ }
190
+
191
+ /**
192
+ * Serialize Message
193
+ * @param {WAConnection} conn
194
+ * @param {Object} m
195
+ * @param {store} store
196
+ */
197
+ exports.smsg = (conn, m, store) => {
198
+ if (!m) return m
199
+ let M = proto.WebMessageInfo
200
+ if (m.key) {
201
+ m.id = m.key.id
202
+ m.isBaileys = m.id.startsWith('BAE5') && m.id.length === 16
203
+ m.chat = m.key.remoteJid
204
+ m.fromMe = m.key.fromMe
205
+ m.isGroup = m.chat.endsWith('@g.us')
206
+ m.sender = m.fromMe ? (conn.user.id.split(":")[0]+'@s.whatsapp.net' || conn.user.id) : (m.key.participant || m.key.remoteJid)
207
+ }
208
+ if (m.message) {
209
+ m.mtype = Object.keys(m.message)[0]
210
+ m.body = m.message.conversation || m.message[m.mtype].caption || m.message[m.mtype].text || (m.mtype == 'listResponseMessage') && m.message[m.mtype].singleSelectReply.selectedRowId || (m.mtype == 'buttonsResponseMessage') && m.message[m.mtype].selectedButtonId || m.mtype
211
+ m.msg = m.message[m.mtype]
212
+ if (m.mtype === 'ephemeralMessage') {
213
+ exports.smsg(hisoka, m.msg)
214
+ m.mtype = m.msg.mtype
215
+ m.msg = m.msg.msg
216
+ }
217
+ let quoted = m.quoted = m.msg.contextInfo ? m.msg.contextInfo.quotedMessage : null
218
+ m.mentionedJid = m.msg.contextInfo ? m.msg.contextInfo.mentionedJid : []
219
+ if (m.quoted) {
220
+ let type = Object.keys(m.quoted)[0]
221
+ m.quoted = m.quoted[type]
222
+ if (['productMessage'].includes(type)) {
223
+ type = Object.keys(m.quoted)[0]
224
+ m.quoted = m.quoted[type]
225
+ }
226
+ if (typeof m.quoted === 'string') m.quoted = {
227
+ text: m.quoted
228
+ }
229
+ m.quoted.mtype = type
230
+ m.quoted.id = m.msg.contextInfo.stanzaId
231
+ m.quoted.chat = m.msg.contextInfo.remoteJid || m.chat
232
+ m.quoted.isBaileys = m.quoted.id ? m.quoted.id.startsWith('BAE5') && m.quoted.id.length === 16 : false
233
+ m.quoted.sender = m.msg.contextInfo.participant.split(":")[0] || m.msg.contextInfo.participant
234
+ m.quoted.fromMe = m.quoted.sender === (conn.user && conn.user.id)
235
+ m.quoted.text = m.quoted.text || m.quoted.caption || ''
236
+ m.quoted.mentionedJid = m.msg.contextInfo ? m.msg.contextInfo.mentionedJid : []
237
+ m.getQuotedObj = m.getQuotedMessage = async () => {
238
+ if (!m.quoted.id) return false
239
+ let q = await store.loadMessage(m.chat, m.quoted.id, conn)
240
+ return exports.smsg(conn, q, store)
241
+ }
242
+ let vM = m.quoted.fakeObj = M.fromObject({
243
+ key: {
244
+ remoteJid: m.quoted.chat,
245
+ fromMe: m.quoted.fromMe,
246
+ id: m.quoted.id
247
+ },
248
+ message: quoted,
249
+ ...(m.isGroup ? { participant: m.quoted.sender } : {})
250
+ })
251
+
252
+ /**
253
+ *
254
+ * @returns
255
+ */
256
+ m.quoted.delete = () => conn.sendMessage(m.quoted.chat, { delete: vM.key })
257
+
258
+ /**
259
+ *
260
+ * @param {*} jid
261
+ * @param {*} forceForward
262
+ * @param {*} options
263
+ * @returns
264
+ */
265
+ m.quoted.copyNForward = (jid, forceForward = false, options = {}) => conn.copyNForward(jid, vM, forceForward, options)
266
+
267
+ /**
268
+ *
269
+ * @returns
270
+ */
271
+ m.quoted.download = () => conn.downloadMediaMessage(m.quoted)
272
+ }
273
+ }
274
+ if (m.msg.url) m.download = () => conn.downloadMediaMessage(m.msg)
275
+ m.text = (m.mtype == 'listResponseMessage' ? m.msg.singleSelectReply.selectedRowId : '') || m.msg.text || m.msg.caption || m.msg || ''
276
+ /**
277
+ * Reply to this message
278
+ * @param {String|Object} text
279
+ * @param {String|false} chatId
280
+ * @param {Object} options
281
+ */
282
+ m.reply = (text, chatId, options) => conn.sendMessage(chatId ? chatId : m.chat, { text: text }, { quoted: m, detectLinks: false, thumbnail: global.thumb, ...options })
283
+ /**
284
+ * Copy this message
285
+ */
286
+ m.copy = () => exports.smsg(conn, M.fromObject(M.toObject(m)))
287
+
288
+ /**
289
+ *
290
+ * @param {*} jid
291
+ * @param {*} forceForward
292
+ * @param {*} options
293
+ * @returns
294
+ */
295
+ m.copyNForward = (jid = m.chat, forceForward = false, options = {}) => conn.copyNForward(jid, m, forceForward, options)
296
+
297
+ return m
298
+ }
299
+
300
+
301
+ let file = require.resolve(__filename)
302
+ fs.watchFile(file, () => {
303
+ fs.unwatchFile(file)
304
+ console.log(chalk.redBright(`Update ${__filename}`))
305
+ delete require.cache[file]
306
+ require(file)
307
+ })
lib/print.js ADDED
@@ -0,0 +1,93 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ let { WAMessageStubType } = require('@adiwajshing/baileys')
2
+ let urlRegex = require('url-regex-safe')({ strict: false })
3
+ let PhoneNumber = require('awesome-phonenumber')
4
+ let terminalImage = global.opts['img'] ? require('terminal-image') : ''
5
+ let chalk = require('chalk')
6
+ let fs = require('fs')
7
+
8
+ module.exports = async function (m, conn = { user: {} }) {
9
+ let _name = await conn.getName(m.sender)
10
+ let sender = PhoneNumber('+' + m.sender.replace('@s.whatsapp.net', '')).getNumber('international') + (_name ? ' ~' + _name : '')
11
+ let chat = await conn.getName(m.chat)
12
+ // let ansi = '\x1b['
13
+ let img
14
+ try {
15
+ if (global.opts['img'])
16
+ img = /sticker|image/gi.test(m.mtype) ? await terminalImage.buffer(await m.download()) : false
17
+ } catch (e) {
18
+ console.error(e)
19
+ }
20
+ let filesize = (m.msg ?
21
+ m.msg.vcard ?
22
+ m.msg.vcard.length :
23
+ m.msg.fileLength ?
24
+ m.msg.fileLength.low || m.msg.fileLength :
25
+ m.msg.axolotlSenderKeyDistributionMessage ?
26
+ m.msg.axolotlSenderKeyDistributionMessage.length :
27
+ m.text ?
28
+ m.text.length :
29
+ 0
30
+ : m.text ? m.text.length : 0) || 0
31
+ let user = global.DATABASE.data.users[m.sender]
32
+ let me = PhoneNumber('+' + (conn.user && conn.user.jid).replace('@s.whatsapp.net', '')).getNumber('international')
33
+ console.log(`▣────────────···
34
+ │ ${chalk.redBright('%s')}\n│⏰ㅤ${chalk.black(chalk.bgYellow('%s'))}\n│📑ㅤ${chalk.black(chalk.bgGreen('%s'))}\n│📊ㅤ${chalk.magenta('%s [%s %sB]')}
35
+ │📤ㅤ${chalk.green('%s')}\n│📃ㅤ${chalk.yellow('%s%s')}\n│📥ㅤ${chalk.green('%s')}\n│💬ㅤ${chalk.black(chalk.bgYellow('%s'))}
36
+ ▣────────────···
37
+ `.trim(),
38
+ me + ' ~' + conn.user.name,
39
+ (m.messageTimestamp ? new Date(1000 * (m.messageTimestamp.low || m.messageTimestamp)) : new Date).toTimeString(),
40
+ m.messageStubType ? WAMessageStubType[m.messageStubType] : '',
41
+ filesize,
42
+ filesize === 0 ? 0 : (filesize / 1009 ** Math.floor(Math.log(filesize) / Math.log(1000))).toFixed(1),
43
+ ['', ...'KMGTP'][Math.floor(Math.log(filesize) / Math.log(1000))] || '',
44
+ sender,
45
+ m ? m.exp : '?',
46
+ user ? '|' + user.exp + '|' + user.limit : '' + ('|' + user.level),
47
+ m.chat + (chat ? ' ~' + chat : ''),
48
+ m.mtype ? m.mtype.replace(/message$/i, '').replace('audio', m.msg.ptt ? 'PTT' : 'audio').replace(/^./, v => v.toUpperCase()) : ''
49
+ )
50
+ if (img) console.log(img.trimEnd())
51
+ if (typeof m.text === 'string' && m.text) {
52
+ let log = m.text.replace(/\u200e+/g, '')
53
+ let mdRegex = /(?<=(?:^|[\s\n])\S?)(?:([*_~])(.+?)\1|```((?:.||[\n\r])+?)```)(?=\S?(?:[\s\n]|$))/g
54
+ let mdFormat = (depth = 4) => (_, type, text, monospace) => {
55
+ let types = {
56
+ _: 'italic',
57
+ '*': 'bold',
58
+ '~': 'strikethrough'
59
+ }
60
+ text = text || monospace
61
+ let formatted = !types[type] || depth < 1 ? text : chalk[types[type]](text.replace(mdRegex, mdFormat(depth - 1)))
62
+ // console.log({ depth, type, formatted, text, monospace }, formatted)
63
+ return formatted
64
+ }
65
+ if (log.length < 4096)
66
+ log = log.replace(urlRegex, (url, i, text) => {
67
+ let end = url.length + i
68
+ return i === 0 || end === text.length || (/^\s$/.test(text[end]) && /^\s$/.test(text[i - 1])) ? chalk.blueBright(url) : url
69
+ })
70
+ log = log.replace(mdRegex, mdFormat(4))
71
+ if (m.mentionedJid) for (let user of m.mentionedJid) log = log.replace('@' + user.split`@`[0], chalk.blueBright('@' + await conn.getName(user)))
72
+ console.log(m.error != null ? chalk.red(log) : m.isCommand ? chalk.yellow(log) : log)
73
+ }
74
+ if (m.messageStubParameters) console.log(m.messageStubParameters.map(jid => {
75
+ jid = conn.decodeJid(jid)
76
+ let name = conn.getName(jid)
77
+ return chalk.gray(PhoneNumber('+' + jid.replace('@s.whatsapp.net', '')).getNumber('international') + (name ? ' ~' + name : ''))
78
+ }).join(', '))
79
+ if (/document/i.test(m.mtype)) console.log(`📄 ${m.msg.filename || m.msg.displayName || 'Document'}`)
80
+ else if (/ContactsArray/i.test(m.mtype)) console.log(`👨‍👩‍👧‍👦 ${' ' || ''}`)
81
+ else if (/contact/i.test(m.mtype)) console.log(`👨 ${m.msg.displayName || ''}`)
82
+ else if (/audio/i.test(m.mtype)) (s = m.msg.seconds, console.log(`${m.msg.ptt ? '🎤 (PTT ' : '🎵 ('}AUDIO) ${Math.floor(s / 60).toString().padStart(2, 0)}:${(s % 60).toString().padStart(2, 0)}`))
83
+
84
+ console.log()
85
+ // if (m.quoted) console.log(m.msg.contextInfo)
86
+ }
87
+
88
+ let file = require.resolve(__filename)
89
+ fs.watchFile(file, () => {
90
+ fs.unwatchFile(file)
91
+ console.log(chalk.redBright("Update 'lib/print.js'"))
92
+ delete require.cache[file]
93
+ })
lib/scrape.js ADDED
@@ -0,0 +1,254 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const cheerio = require('cheerio')
2
+ const fetch = require('node-fetch')
3
+ const axios = require("axios")
4
+ const qs = require("qs")
5
+
6
+ function quotes(input) {
7
+ return new Promise((resolve, reject) => {
8
+ fetch('https://jagokata.com/kata-bijak/kata-' + input.replace(/\s/g, '_') + '.html?page=1')
9
+ .then(res => res.text())
10
+ .then(res => {
11
+ const $ = cheerio.load(res)
12
+ data = []
13
+ $('div[id="main"]').find('ul[id="citatenrijen"] > li').each(function (index, element) {
14
+ x = $(this).find('div[class="citatenlijst-auteur"] > a').text().trim()
15
+ y = $(this).find('span[class="auteur-beschrijving"]').text().trim()
16
+ z = $(element).find('q[class="fbquote"]').text().trim()
17
+ data.push({ author: x, bio: y, quote: z })
18
+ })
19
+ data.splice(2, 1)
20
+ if (data.length == 0) return resolve({ creator: 'stikerin', status: false })
21
+ resolve({ creator: 'stikerin', status: true, data })
22
+ }).catch(reject)
23
+ })
24
+ }
25
+
26
+ function joox(query) {
27
+ return new Promise((resolve, reject) => {
28
+ const time = Math.floor(new Date() / 1000)
29
+ axios.get('http://api.joox.com/web-fcgi-bin//web_search?lang=id&country=id&type=0&search_input=' + query + '&pn=1&sin=0&ein=29&_=' + time)
30
+ .then(({ data }) => {
31
+ let result = []
32
+ let hasil = []
33
+ let promoses = []
34
+ let ids = []
35
+ data.itemlist.forEach(result => {
36
+ ids.push(result.songid)
37
+ });
38
+ for (let i = 0; i < data.itemlist.length; i++) {
39
+ const get = 'http://api.joox.com/web-fcgi-bin/web_get_songinfo?songid=' + ids[i]
40
+ promoses.push(
41
+ axios.get(get, {
42
+ headers: {
43
+ Cookie: 'wmid=142420656; user_type=1; country=id; session_key=2a5d97d05dc8fe238150184eaf3519ad;'
44
+ }
45
+ })
46
+ .then(({ data }) => {
47
+ const res = JSON.parse(data.replace('MusicInfoCallback(', '').replace('\n)', ''))
48
+ hasil.push({
49
+ lagu: res.msong,
50
+ album: res.malbum,
51
+ penyanyi: res.msinger,
52
+ publish: res.public_time,
53
+ img: res.imgSrc,
54
+ mp3: res.mp3Url
55
+ })
56
+ Promise.all(promoses).then(() => resolve({
57
+ creator: "ariffb",
58
+ status: true,
59
+ data: hasil,
60
+ }))
61
+ }).catch(reject)
62
+ )
63
+ }
64
+ }).catch(reject)
65
+ })
66
+ }
67
+
68
+ function tiktok(url) {
69
+ return new Promise(async (resolve, reject) => {
70
+ axios.get('https://ttdownloader.com/', {
71
+ headers: {
72
+ "accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9",
73
+ "user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36",
74
+ "cookie": "PHPSESSID=9ut8phujrprrmll6oc3bist01t; popCookie=1; _ga=GA1.2.1068750365.1625213061; _gid=GA1.2.842420949.1625213061"
75
+ }
76
+ })
77
+ .then(({ data }) => {
78
+ const $ = cheerio.load(data)
79
+ let token = $('#token').attr('value')
80
+ let config = {
81
+ 'url': url,
82
+ 'format': '',
83
+ 'token': token
84
+ }
85
+ axios('https://ttdownloader.com/req/', {
86
+ method: 'POST',
87
+ data: new URLSearchParams(Object.entries(config)),
88
+ headers: {
89
+ "accept": "text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9",
90
+ "user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36",
91
+ "cookie": "PHPSESSID=9ut8phujrprrmll6oc3bist01t; popCookie=1; _ga=GA1.2.1068750365.1625213061; _gid=GA1.2.842420949.1625213061"
92
+ }
93
+ })
94
+ .then(({ data }) => {
95
+ const $ = cheerio.load(data)
96
+ resolve({
97
+ nowm: $('div:nth-child(2) > div.download > a').attr('href'),
98
+ wm: $('div:nth-child(3) > div.download > a').attr('href'),
99
+ audio: $('div:nth-child(4) > div.download > a').attr('href')
100
+ })
101
+ })
102
+ })
103
+ .catch(reject)
104
+ })
105
+ }
106
+
107
+ function twitter(url) {
108
+ return new Promise((resolve, reject) => {
109
+ let params = new URLSearchParams()
110
+ params.append('URL', url)
111
+ fetch('https://twdown.net/download.php', { method: 'POST', body: params })
112
+ .then(res => res.text())
113
+ .then(res => {
114
+ const $ = cheerio.load(res);
115
+ data = []
116
+ $('div.container').find('tbody > tr > td').each(function (index, element) {
117
+ x = $(this).find('a').attr('href')
118
+ if (x !== '#') {
119
+ if (typeof x !== 'undefined') {
120
+ data.push({ url: x })
121
+ }
122
+ }
123
+ })
124
+ if (data.length == 0) return resolve({ status: false })
125
+ resolve({ status: true, data })
126
+ }).catch(reject)
127
+ })
128
+ }
129
+
130
+ function igdl(url) {
131
+ return new Promise(async (resolve, reject) => {
132
+ axios.request({
133
+ url: 'https://www.instagramsave.com/download-instagram-videos.php',
134
+ method: 'GET',
135
+ headers: {
136
+ "user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36",
137
+ "cookie": "PHPSESSID=ugpgvu6fgc4592jh7ht9d18v49; _ga=GA1.2.1126798330.1625045680; _gid=GA1.2.1475525047.1625045680; __gads=ID=92b58ed9ed58d147-221917af11ca0021:T=1625045679:RT=1625045679:S=ALNI_MYnQToDW3kOUClBGEzULNjeyAqOtg"
138
+ }
139
+ })
140
+ .then(({ data }) => {
141
+ const $ = cheerio.load(data)
142
+ const token = $('#token').attr('value')
143
+ let config = {
144
+ headers: {
145
+ 'content-type': 'application/x-www-form-urlencoded; charset=UTF-8',
146
+ "sec-ch-ua": '" Not;A Brand";v="99", "Google Chrome";v="91", "Chromium";v="91"',
147
+ "cookie": "PHPSESSID=ugpgvu6fgc4592jh7ht9d18v49; _ga=GA1.2.1126798330.1625045680; _gid=GA1.2.1475525047.1625045680; __gads=ID=92b58ed9ed58d147-221917af11ca0021:T=1625045679:RT=1625045679:S=ALNI_MYnQToDW3kOUClBGEzULNjeyAqOtg",
148
+ "user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36",
149
+ },
150
+ data: {
151
+ 'url': url,
152
+ 'action': 'post',
153
+ 'token': token
154
+ }
155
+ }
156
+ axios.post('https://www.instagramsave.com/system/action.php', qs.stringify(config.data), { headers: config.headers })
157
+ .then(({ data }) => {
158
+ resolve(data.medias)
159
+ })
160
+ })
161
+ .catch(reject)
162
+ })
163
+ }
164
+
165
+ function igstory(username) {
166
+ return new Promise(async (resolve, reject) => {
167
+ axios.request({
168
+ url: 'https://www.instagramsave.com/instagram-story-downloader.php',
169
+ method: 'GET',
170
+ headers: {
171
+ "user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36",
172
+ "cookie": "PHPSESSID=ugpgvu6fgc4592jh7ht9d18v49; _ga=GA1.2.1126798330.1625045680; _gid=GA1.2.1475525047.1625045680; __gads=ID=92b58ed9ed58d147-221917af11ca0021:T=1625045679:RT=1625045679:S=ALNI_MYnQToDW3kOUClBGEzULNjeyAqOtg"
173
+ }
174
+ })
175
+ .then(({ data }) => {
176
+ const $ = cheerio.load(data)
177
+ const token = $('#token').attr('value')
178
+ let config = {
179
+ headers: {
180
+ 'content-type': 'application/x-www-form-urlencoded; charset=UTF-8',
181
+ "sec-ch-ua": '" Not;A Brand";v="99", "Google Chrome";v="91", "Chromium";v="91"',
182
+ "cookie": "PHPSESSID=ugpgvu6fgc4592jh7ht9d18v49; _ga=GA1.2.1126798330.1625045680; _gid=GA1.2.1475525047.1625045680; __gads=ID=92b58ed9ed58d147-221917af11ca0021:T=1625045679:RT=1625045679:S=ALNI_MYnQToDW3kOUClBGEzULNjeyAqOtg",
183
+ "user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36",
184
+ },
185
+ data: {
186
+ 'url': 'https://www.instagram.com/' + username,
187
+ 'action': 'story',
188
+ 'token': token
189
+ }
190
+ }
191
+ axios.post('https://www.instagramsave.com/system/action.php', qs.stringify(config.data), { headers: config.headers })
192
+ .then(({ data }) => {
193
+ resolve(data.medias)
194
+ })
195
+ })
196
+ .catch(reject)
197
+ })
198
+ }
199
+
200
+ function pin(url) {
201
+ return new Promise(async (resolve, reject) => {
202
+ let form = new URLSearchParams()
203
+ form.append('url', url)
204
+ let html = await (await fetch('https://pinterestvideodownloader.com/', { method: 'POST', body: form })).text()
205
+ $ = cheerio.load(html)
206
+ let data = []
207
+ $('table > tbody > tr').each(function (i, e) {
208
+ if ($($(e).find('td')[0]).text() != '') data.push({
209
+ url: $($(e).find('td')[0]).find('a').attr('href')
210
+ })
211
+ })
212
+ if (data.length == 0) return resolve({ status: false })
213
+ resolve({ status: true, data })
214
+ })
215
+ }
216
+
217
+
218
+ let is = {
219
+ headers: {
220
+ 'content-type': 'application/x-www-form-urlencoded; charset=UTF-8',
221
+ "sec-ch-ua": '" Not;A Brand";v="99", "Google Chrome";v="91", "Chromium";v="91"',
222
+ "cookie": "PHPSESSID=ugpgvu6fgc4592jh7ht9d18v49; _ga=GA1.2.1126798330.1625045680; _gid=GA1.2.1475525047.1625045680; __gads=ID=92b58ed9ed58d147-221917af11ca0021:T=1625045679:RT=1625045679:S=ALNI_MYnQToDW3kOUClBGEzULNjeyAqOtg",
223
+ "user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36",
224
+ }
225
+ }
226
+
227
+ function _token(host) {
228
+ return new Promise(async (resolve, reject) => {
229
+ axios.request({
230
+ url: host, method: 'GET', headers: {
231
+ "user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36",
232
+ "cookie": "PHPSESSID=ugpgvu6fgc4592jh7ht9d18v49; _ga=GA1.2.1126798330.1625045680; _gid=GA1.2.1475525047.1625045680; __gads=ID=92b58ed9ed58d147-221917af11ca0021:T=1625045679:RT=1625045679:S=ALNI_MYnQToDW3kOUClBGEzULNjeyAqOtg"
233
+ }
234
+ }).then(({ data }) => {
235
+ let $ = cheerio.load(data)
236
+ let token = $('#token').attr('value')
237
+ resolve(token)
238
+ })
239
+ })
240
+ }
241
+
242
+ function facebook(url) {
243
+ return new Promise(async (resolve, reject) => {
244
+ let host = 'https://aiovideodl.ml/'
245
+ let form = { data: { 'url': url, 'token': (await _token(host)) } }
246
+ axios.post(host + '/system/action.php', qs.stringify(form.data), { headers: is.headers })
247
+ .then(({ data }) => {
248
+ if (data.links.lenght == 0) return resolve({ creator: '@neoxrs – Wildan Izzudin', status: false })
249
+ resolve({ creator: '@neoxrs – Wildan Izzudin', status: true, data: data.links })
250
+ })
251
+ })
252
+ }
253
+
254
+ module.exports = { facebook, quotes, igdl, igstory, tiktok, twitter, joox, pin }
lib/simple.js ADDED
@@ -0,0 +1,1638 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const { imageToWebp, videoToWebp, writeExifImg, writeExifVid } = require('../lib/exif')
2
+ const {
3
+ default: makeWASocket,
4
+ makeWALegacySocket,
5
+ extractMessageContent,
6
+ makeInMemoryStore,
7
+ proto,
8
+ prepareWAMessageMedia,
9
+ downloadContentFromMessage,
10
+ getBinaryNodeChild,
11
+ jidDecode,
12
+ areJidsSameUser,
13
+ generateForwardMessageContent,
14
+ generateWAMessageFromContent,
15
+ WAMessageStubType,
16
+ WA_DEFAULT_EPHEMERAL,
17
+ } = require('@adiwajshing/baileys')
18
+ const { toAudio, toPTT, toVideo } = require('./converter')
19
+ const chalk = require('chalk')
20
+ const fetch = require('node-fetch')
21
+ const FileType = require('file-type')
22
+ const PhoneNumber = require('awesome-phonenumber')
23
+ const fs = require('fs')
24
+ const path = require('path')
25
+ const jimp = require('jimp')
26
+ const pino = require('pino')
27
+ const util = require('util')
28
+ const store = makeInMemoryStore({ logger: pino().child({ level: 'silent', stream: 'store' }) })
29
+
30
+
31
+ exports.makeWASocket = (connectionOptions, options = {}) => {
32
+ let conn = (opts['legacy'] ? makeWALegacySocket : makeWASocket)(connectionOptions)
33
+ // conn.ws.on('CB:stream:error', (stream) => {
34
+ // const { code } = stream || {}
35
+ // if (code == '401') conn.ev.emit('connection.update', {
36
+ // connection: 'logged Out',
37
+ // lastDisconnect: {
38
+ // error: {
39
+ // output: {
40
+ // statusCode: DisconnectReason.loggedOut
41
+ // }
42
+ // },
43
+ // date: new Date()
44
+ // }
45
+ // })
46
+ // })
47
+ conn.decodeJid = (jid) => {
48
+ if (!jid) return jid
49
+ if (/:\d+@/gi.test(jid)) {
50
+ const decode = jidDecode(jid) || {}
51
+ return decode.user && decode.server && decode.user + '@' + decode.server || jid
52
+ } else return jid
53
+ }
54
+ if (conn.user && conn.user.id) conn.user.jid = conn.decodeJid(conn.user.id)
55
+ if (!conn.chats) conn.chats = {}
56
+
57
+ function updateNameToDb(contacts) {
58
+ if (!contacts) return
59
+ for (const contact of contacts) {
60
+ const id = conn.decodeJid(contact.id)
61
+ if (!id) continue
62
+ let chats = conn.chats[id]
63
+ if (!chats) chats = conn.chats[id] = { id }
64
+ conn.chats[id] = {
65
+ ...chats,
66
+ ...({
67
+ ...contact, id, ...(id.endsWith('@g.us') ?
68
+ { subject: contact.subject || chats.subject || '' } :
69
+ { name: contact.notify || chats.name || chats.notify || '' })
70
+ } || {})
71
+ }
72
+ }
73
+ }
74
+
75
+
76
+ conn.ev.on('contacts.upsert', updateNameToDb)
77
+ conn.ev.on('groups.update', updateNameToDb)
78
+ conn.ev.on('chats.set', async ({ chats }) => {
79
+ for (const { id, name, readOnly } of chats) {
80
+ id = conn.decodeJid(id)
81
+ if (!id) continue
82
+ const isGroup = id.endsWith('@g.us')
83
+ let chats = conn.chats[id]
84
+ if (!chats) chats = conn.chats[id] = { id }
85
+ chats.isChats = !readOnly
86
+ if (name) chats[isGroup ? 'subject' : 'name'] = name
87
+ if (isGroup) {
88
+ const metadata = await conn.groupMetadata(id).catch(_ => null)
89
+ if (!metadata) continue
90
+ chats.subject = name || metadata.subject
91
+ chats.metadata = metadata
92
+ }
93
+ }
94
+ })
95
+ conn.ev.on('group-participants.update', async function updateParticipantsToDb({ id, participants, action }) {
96
+ id = conn.decodeJid(id)
97
+ if (!(id in conn.chats)) conn.chats[id] = { id }
98
+ conn.chats[id].isChats = true
99
+ const groupMetadata = await conn.groupMetadata(id).catch(_ => null)
100
+ if (!groupMetadata) return
101
+ conn.chats[id] = {
102
+ ...conn.chats[id],
103
+ subject: groupMetadata.subject,
104
+ metadata: groupMetadata
105
+ }
106
+ })
107
+
108
+ conn.ev.on('groups.update', async function groupUpdatePushToDb(groupsUpdates) {
109
+ for (const update of groupsUpdates) {
110
+ const id = conn.decodeJid(update.id)
111
+ if (!id) continue
112
+ const isGroup = id.endsWith('@g.us')
113
+ if (!isGroup) continue
114
+ let chats = conn.chats[id]
115
+ if (!chats) chats = conn.chats[id] = { id }
116
+ chats.isChats = true
117
+ const metadata = await conn.groupMetadata(id).catch(_ => null)
118
+ if (!metadata) continue
119
+ chats.subject = metadata.subject
120
+ chats.metadata = metadata
121
+ }
122
+ })
123
+ conn.ev.on('chats.upsert', async function chatsUpsertPushToDb(chatsUpsert) {
124
+ console.log({ chatsUpsert })
125
+ const { id, name } = chatsUpsert
126
+ if (!id) return
127
+ let chats = conn.chats[id] = { ...conn.chats[id], ...chatsUpsert, isChats: true }
128
+ const isGroup = id.endsWith('@g.us')
129
+ if (isGroup) {
130
+ const metadata = await conn.groupMetadata(id).catch(_ => null)
131
+ if (metadata) {
132
+ chats.subject = name || metadata.subject
133
+ chats.metadata = metadata
134
+ }
135
+ const groups = await conn.groupFetchAllParticipating().catch(_ => ({})) || {}
136
+ for (const group in groups) conn.chats[group] = { id: group, subject: groups[group].subject, isChats: true, metadata: groups[group] }
137
+ }
138
+ })
139
+ conn.ev.on('presence.update', async function presenceUpdatePushToDb({ id, presences }) {
140
+ const sender = Object.keys(presences)[0] || id
141
+ const _sender = conn.decodeJid(sender)
142
+ const presence = presences[sender]['lastKnownPresence'] || 'composing'
143
+ let chats = conn.chats[_sender]
144
+ if (!chats) chats = conn.chats[_sender] = { id: sender }
145
+ chats.presences = presence
146
+ if (id.endsWith('@g.us')) {
147
+ let chats = conn.chats[id]
148
+ if (!chats) {
149
+ const metadata = await conn.groupMetadata(id).catch(_ => null)
150
+ if (metadata) chats = conn.chats[id] = { id, subject: metadata.subject, metadata }
151
+ }
152
+ chats.isChats = true
153
+ }
154
+ })
155
+
156
+ conn.logger = {
157
+ ...conn.logger,
158
+ info(...args) { console.log(chalk.bold.rgb(57, 183, 16)(`INFO [${chalk.rgb(255, 255, 255)(new Date())}]:`), chalk.cyan(util.format(...args))) },
159
+ error(...args) { console.log(chalk.bold.rgb(247, 38, 33)(`ERROR [${chalk.rgb(255, 255, 255)(new Date())}]:`), chalk.rgb(255, 38, 0)(util.format(...args))) },
160
+ warn(...args) { console.log(chalk.bold.rgb(239, 225, 3)(`WARNING [${chalk.rgb(255, 255, 255)(new Date())}]:`), chalk.keyword('orange')(util.format(...args))) }
161
+ }
162
+
163
+
164
+ /**
165
+ * getBuffer hehe
166
+ * @param {fs.PathLike} path
167
+ * @param {Boolean} returnFilename
168
+ */
169
+ conn.getFile = async (PATH, returnAsFilename) => {
170
+ let res, filename
171
+ let data = Buffer.isBuffer(PATH) ? PATH : /^data:.*?\/.*?;base64,/i.test(PATH) ? Buffer.from(PATH.split`,`[1], 'base64') : /^https?:\/\//.test(PATH) ? await (res = await fetch(PATH)).buffer() : fs.existsSync(PATH) ? (filename = PATH, fs.readFileSync(PATH)) : typeof PATH === 'string' ? PATH : Buffer.alloc(0)
172
+ if (!Buffer.isBuffer(data)) throw new TypeError('Result is not a buffer')
173
+ let type = await FileType.fromBuffer(data) || {
174
+ mime: 'application/octet-stream',
175
+ ext: '.bin'
176
+ }
177
+ if (data && returnAsFilename && !filename) (filename = path.join(__dirname, '../tmp/' + new Date * 1 + '.' + type.ext), await fs.promises.writeFile(filename, data))
178
+ return {
179
+ res,
180
+ filename,
181
+ ...type,
182
+ data
183
+ }
184
+ }
185
+
186
+ /**
187
+ * waitEvent
188
+ * @param {Partial<BaileysEventMap>|String} eventName
189
+ * @param {Boolean} is
190
+ * @param {Number} maxTries
191
+ * @returns
192
+ */
193
+ conn.waitEvent = (eventName, is = () => true, maxTries = 25) => {
194
+ return new Promise((resolve, reject) => {
195
+ let tries = 0
196
+ let on = (...args) => {
197
+ if (++tries > maxTries) reject('Max tries reached')
198
+ else if (is()) {
199
+ conn.ev.off(eventName, on)
200
+ resolve(...args)
201
+ }
202
+ }
203
+ conn.ev.on(eventName, on)
204
+ })
205
+ }
206
+
207
+ conn.delay = (ms) => new Promise((resolve) => setTimeout(resolve, ms))
208
+
209
+ /**
210
+ *
211
+ * @param {String} text
212
+ * @returns
213
+ */
214
+ conn.filter = (text) => {
215
+ let mati = ["q", "w", "r", "t", "y", "p", "s", "d", "f", "g", "h", "j", "k", "l", "z", "x", "c", "v", "b", "n", "m"]
216
+ if (/[aiueo][aiueo]([qwrtypsdfghjklzxcvbnm])?$/i.test(text)) return text.substring(text.length - 1)
217
+ else {
218
+ let res = Array.from(text).filter(v => mati.includes(v))
219
+ let resu = res[res.length - 1]
220
+ for (let huruf of mati) {
221
+ if (text.endsWith(huruf)) {
222
+ resu = res[res.length - 2]
223
+ }
224
+ }
225
+ let misah = text.split(resu)
226
+ return resu + misah[misah.length - 1]
227
+ }
228
+ }
229
+
230
+ /**
231
+ * ms to date
232
+ * @param {String} ms
233
+ */
234
+ conn.msToDate = (ms) => {
235
+ let days = Math.floor(ms / (24 * 60 * 60 * 1000));
236
+ let daysms = ms % (24 * 60 * 60 * 1000);
237
+ let hours = Math.floor((daysms) / (60 * 60 * 1000));
238
+ let hoursms = ms % (60 * 60 * 1000);
239
+ let minutes = Math.floor((hoursms) / (60 * 1000));
240
+ let minutesms = ms % (60 * 1000);
241
+ let sec = Math.floor((minutesms) / (1000));
242
+ return days + " Hari " + hours + " Jam " + minutes + " Menit";
243
+ // +minutes+":"+sec;
244
+ }
245
+
246
+ /**
247
+ * isi
248
+ */
249
+ conn.rand = async (isi) => {
250
+ return isi[Math.floor(Math.random() * isi.length)]
251
+ }
252
+
253
+ /**
254
+ * For Resize the Image By Aine
255
+ * @param {Buffer} image
256
+ * @param {String} ukuran height
257
+ * @param {String} ukuran weight
258
+ * @returns
259
+ */
260
+
261
+ conn.resize = async (buffer, uk1, uk2) => {
262
+ return new Promise(async(resolve, reject) => {
263
+ var baper = await jimp.read(buffer);
264
+ var ab = await baper.resize(uk1, uk2).getBufferAsync(jimp.MIME_JPEG)
265
+ resolve(ab)
266
+ })
267
+ }
268
+
269
+ /**
270
+ * Send Media All Type
271
+ * @param {String} jid
272
+ * @param {String|Buffer} path
273
+ * @param {Object} quoted
274
+ * @param {Object} options
275
+ */
276
+ conn.sendMedia = async (jid, path, quoted, options = {}) => {
277
+ let { ext, mime, data } = await conn.getFile(path)
278
+ messageType = mime.split("/")[0]
279
+ pase = messageType.replace('application', 'document') || messageType
280
+ return await conn.sendMessage(jid, { [`${pase}`]: data, mimetype: mime, ...options }, { quoted })
281
+ }
282
+
283
+ /**
284
+ * Send Media/File with Automatic Type Specifier
285
+ * @param {String} jid
286
+ * @param {String|Buffer} path
287
+ * @param {String} filename
288
+ * @param {String} caption
289
+ * @param {proto.WebMessageInfo} quoted
290
+ * @param {Boolean} ptt
291
+ * @param {Object} options
292
+ */
293
+ conn.getFile = async (PATH, returnAsFilename) => {
294
+ let res, filename
295
+ let data = Buffer.isBuffer(PATH) ? PATH : /^data:.*?\/.*?;base64,/i.test(PATH) ? Buffer.from(PATH.split`,`[1], 'base64') : /^https?:\/\//.test(PATH) ? await (res = await fetch(PATH)).buffer() : fs.existsSync(PATH) ? (filename = PATH, fs.readFileSync(PATH)) : typeof PATH === 'string' ? PATH : Buffer.alloc(0)
296
+ if (!Buffer.isBuffer(data)) throw new TypeError('Result is not a buffer')
297
+ let type = await FileType.fromBuffer(data) || {
298
+ mime: 'application/octet-stream',
299
+ ext: '.bin'
300
+ }
301
+ if (data && returnAsFilename && !filename) (filename = path.join(__dirname, '../tmp/' + new Date * 1 + '.' + type.ext), await fs.promises.writeFile(filename, data))
302
+ return {
303
+ res,
304
+ filename,
305
+ ...type,
306
+ data
307
+ }
308
+ }
309
+ /**
310
+ * Send Media/File with Automatic Type Specifier
311
+ * @param {String} jid
312
+ * @param {String|Buffer} path
313
+ * @param {String} filename
314
+ * @param {String} caption
315
+ * @param {Object} quoted
316
+ * @param {Boolean} ptt
317
+ * @param {Object} options
318
+ */
319
+ conn.sendFile = async (jid, path, filename = '', caption = '', quoted, ptt = false, options = {}) => {
320
+ let type = await conn.getFile(path, true)
321
+ let { res, data: file, filename: pathFile } = type
322
+ if (res && res.status !== 200 || file.length <= 65536) {
323
+ try { throw { json: JSON.parse(file.toString()) } }
324
+ catch (e) { if (e.json) throw e.json }
325
+ }
326
+ let opt = { filename }
327
+ if (quoted) opt.quoted = quoted
328
+ if (!type) if (options.asDocument) options.asDocument = true
329
+ let mtype = '', mimetype = type.mime
330
+ if (/webp/.test(type.mime)) mtype = 'sticker'
331
+ else if (/image/.test(type.mime)) mtype = 'image'
332
+ else if (/video/.test(type.mime)) mtype = 'video'
333
+ else if (/audio/.test(type.mime)) (
334
+ convert = await (ptt ? toPTT : toAudio)(file, type.ext),
335
+ file = convert.data,
336
+ pathFile = convert.filename,
337
+ mtype = 'audio',
338
+ mimetype = 'audio/ogg; codecs=opus'
339
+ )
340
+ else mtype = 'document'
341
+ return await conn.sendMessage(jid, {
342
+ ...options,
343
+ caption,
344
+ ptt,
345
+ [mtype]: { url: pathFile },
346
+ mimetype
347
+ }, {
348
+ ...opt,
349
+ ...options
350
+ })
351
+ }
352
+ //Wm Sticker
353
+ conn.sendImageAsSticker = async (jid, path, quoted, options = {}) => {
354
+ let buff = Buffer.isBuffer(path) ? path : /^data:.*?\/.*?;base64,/i.test(path) ? Buffer.from(path.split`,`[1], 'base64') : /^https?:\/\//.test(path) ? await (await fetch(path)).buffer() : fs.existsSync(path) ? fs.readFileSync(path) : Buffer.alloc(0)
355
+ let buffer
356
+ if (options && (options.packname || options.author)) {
357
+ buffer = await writeExifImg(buff, options)
358
+ } else {
359
+ buffer = await imageToWebp(buff)
360
+ }
361
+
362
+ await conn.sendMessage(jid, { sticker: { url: buffer }, ...options }, { quoted })
363
+ return buffer
364
+ }
365
+ conn.sendVideoAsSticker = async (jid, path, quoted, options = {}) => {
366
+ let buff = Buffer.isBuffer(path) ? path : /^data:.*?\/.*?;base64,/i.test(path) ? Buffer.from(path.split`,`[1], 'base64') : /^https?:\/\//.test(path) ? await (await fetch(path)).buffer() : fs.existsSync(path) ? fs.readFileSync(path) : Buffer.alloc(0)
367
+ let buffer
368
+ if (options && (options.packname || options.author)) {
369
+ buffer = await writeExifVid(buff, options)
370
+ } else {
371
+ buffer = await videoToWebp(buff)
372
+ }
373
+
374
+ await conn.sendMessage(jid, { sticker: { url: buffer }, ...options }, { quoted })
375
+ return buffer
376
+ }
377
+ /**
378
+ * Send Contact
379
+ * @param {String} jid
380
+ * @param {String[][]} data
381
+ * @param {proto.WebMessageInfo} quoted
382
+ * @param {Object} options
383
+ */
384
+ conn.sendContact = async (jid, data, quoted, options) => {
385
+ let contacts = []
386
+ for (let [number, name] of data) {
387
+ number = number.replace(/[^0-9]/g, '')
388
+ let njid = number + '@s.whatsapp.net'
389
+ let biz = await conn.getBusinessProfile(njid) || {}
390
+ // N:;${name.replace(/\n/g, '\\n').split(' ').reverse().join(';')};;;
391
+ let vcard = `
392
+ BEGIN:VCARD
393
+ VERSION:3.0
394
+ FN:${name.replace(/\n/g, '\\n')}
395
+ item1.TEL;waid=${number}:${PhoneNumber('+' + number).getNumber('international')}
396
+ item1.X-ABLabel:Ponsel${biz.description ? `
397
+ PHOTO;BASE64:${(await conn.getFile(await conn.profilePictureUrl(njid)).catch(_ => ({})) || {}).data?.toString('base64')}
398
+ X-WA-BIZ-DESCRIPTION:${(biz.description || '').replace(/\n/g, '\\n')}
399
+ X-WA-BIZ-NAME:${(((conn.chats[njid] || {}) || { vname: conn.chats[njid]?.name }).vname || conn.getName(njid) || name).replace(/\n/, '\\n')}
400
+ `.trim() : ''}
401
+ END:VCARD
402
+ `.trim()
403
+ contacts.push({ vcard, displayName: name })
404
+
405
+ }
406
+ return await conn.sendMessage(jid, {
407
+ contacts: {
408
+ ...options,
409
+ displayName: (contacts.length > 1 ? `${contacts.length} kontak` : contacts[0].displayName) || null,
410
+ contacts,
411
+ },
412
+ quoted, ...options
413
+ })
414
+ }
415
+
416
+ /**
417
+ * Reply to a message
418
+ * @param {String} jid
419
+ * @param {String|Object} text
420
+ * @param {Object} quoted
421
+ * @param {Object} options
422
+ */
423
+ conn.reply = (jid, text = '', quoted, options) => {
424
+ return Buffer.isBuffer(text) ? this.sendFile(jid, text, 'file', '', quoted, false, options) : conn.sendMessage(jid, { ...options, text, mentions: conn.parseMention(text) }, { quoted, ...options, mentions: conn.parseMention(text) })
425
+ }
426
+
427
+ conn.decodeJid = (jid) => {
428
+ if (!jid) return jid
429
+ if (/:\d+@/gi.test(jid)) {
430
+ let decode = jidDecode(jid) || {}
431
+ return decode.user && decode.server && decode.user + '@' + decode.server || jid
432
+ } else return jid
433
+ }
434
+
435
+ /**
436
+ *
437
+ * @param {*} jid
438
+ * @param {*} text
439
+ * @param {*} quoted
440
+ * @param {*} options
441
+ * @returns
442
+ */
443
+ conn.sendText = (jid, text, quoted = '', options) => conn.sendMessage(jid, { text: text, ...options }, { quoted })
444
+
445
+ /**
446
+ * sendGroupV4Invite
447
+ * @param {String} jid
448
+ * @param {*} participant
449
+ * @param {String} inviteCode
450
+ * @param {Number} inviteExpiration
451
+ * @param {String} groupName
452
+ * @param {String} caption
453
+ * @param {*} options
454
+ * @returns
455
+ */
456
+ conn.sendGroupV4Invite = async (jid, participant, inviteCode, inviteExpiration, groupName = 'unknown subject', caption = 'Invitation to join my WhatsApp group', options = {}) => {
457
+ let msg = proto.Message.fromObject({
458
+ groupInviteMessage: proto.GroupInviteMessage.fromObject({
459
+ inviteCode,
460
+ inviteExpiration: parseInt(inviteExpiration) || + new Date(new Date + (3 * 86400000)),
461
+ groupJid: jid,
462
+ groupName: groupName ? groupName : this.getName(jid),
463
+ caption
464
+ })
465
+ })
466
+ let message = await this.prepareMessageFromContent(participant, msg, options)
467
+ await this.relayWAMessage(message)
468
+ return message
469
+ }
470
+
471
+ /**
472
+ * send Button
473
+ * @param {String} jid
474
+ * @param {String} contentText
475
+ * @param {String} footer
476
+ * @param {Buffer|String} buffer
477
+ * @param {String[]} buttons
478
+ * @param {proto.WebMessageInfo} quoted
479
+ * @param {Object} options
480
+ */
481
+ conn.sendButton = async (jid, contentText, footer, buffer, buttons, quoted, options) => {
482
+ if (buffer) try { buffer = (await conn.getFile(buffer)).data } catch { buffer = null }
483
+ let message = {
484
+ ...options,
485
+ ...(buffer ? { caption: contentText || '' } : { text: contentText || '' }),
486
+ footer,
487
+ buttons: buttons.map(btn => {
488
+ return {
489
+ buttonId: btn[1] || btn[0] || '',
490
+ buttonText: {
491
+ displayText: btn[0] || btn[1] || ''
492
+ }
493
+ }
494
+ }),
495
+ ...(buffer ? { image: buffer } : {})
496
+ }
497
+ return await conn.sendMessage(jid, message, {
498
+ quoted,
499
+ upload: conn.waUploadToServer,
500
+ ...options
501
+ })
502
+ }
503
+
504
+ conn.sendBut = async(jid, content, footer, button1, row1, quoted) => {
505
+ const buttons = [
506
+ {buttonId: row1, buttonText: {displayText: button1}, type: 1}
507
+ ]
508
+ const buttonMessage = {
509
+ text: content,
510
+ footer: footer,
511
+ buttons: buttons,
512
+ headerType: 1,
513
+ mentions: conn.parseMention(footer+content)
514
+ }
515
+ return await conn.sendMessage(jid, buttonMessage, {quoted})
516
+ }
517
+
518
+ conn.send2But = async(jid, content, footer, button1, row1, button2, row2, quoted) => {
519
+ const buttons = [
520
+ { buttonId: row1, buttonText: { displayText: button1 }, type: 1 },
521
+ { buttonId: row2, buttonText: { displayText: button2 }, type: 1 }
522
+ ]
523
+ const buttonMessage = {
524
+ text: content,
525
+ footer: footer,
526
+ buttons: buttons,
527
+ headerType: 1
528
+ }
529
+ return await conn.sendMessage(jid, buttonMessage, {quoted})
530
+ }
531
+
532
+ conn.send3But = async(jid, content, footer,button1, row1, button2, row2, button3, row3, quoted) => {
533
+ const buttons = [
534
+ { buttonId: row1, buttonText: { displayText: button1 }, type: 1 },
535
+ { buttonId: row2, buttonText: { displayText: button2 }, type: 1 },
536
+ { buttonId: row3, buttonText: { displayText: button3 }, type: 1 }
537
+ ]
538
+ const buttonMessage = {
539
+ text: content,
540
+ footer: footer,
541
+ buttons: buttons,
542
+ headerType: 1
543
+ }
544
+ return await conn.sendMessage(jid, buttonMessage, {quoted})
545
+ }
546
+ conn.send4But = async(jid, content, footer,button1, row1, button2, row2, button3, row3, button4, row4, quoted) => {
547
+ const buttons = [
548
+ { buttonId: row1, buttonText: { displayText: button1 }, type: 1 },
549
+ { buttonId: row2, buttonText: { displayText: button2 }, type: 1 },
550
+ { buttonId: row3, buttonText: { displayText: button3 }, type: 1 },
551
+ { buttonId: row4, buttonText: { displayText: button4 }, type: 1 }
552
+ ]
553
+ const buttonMessage = {
554
+ text: content,
555
+ footer: footer,
556
+ buttons: buttons,
557
+ headerType: 1
558
+ }
559
+ return await conn.sendMessage(jid, buttonMessage, {quoted})
560
+ }
561
+ /**
562
+ * send Button Img
563
+ * @param {String} jid
564
+ * @param {String} contentText
565
+ * @param {String} footer
566
+ * @param {Buffer|String} buffer
567
+ * @param {String[]} buttons
568
+ * @param {Object} quoted
569
+ * @param {Object} options
570
+ */
571
+ conn.sendButtonImg = async (jid, buffer, contentText, footerText, button1, id1, quoted, options) => {
572
+ let type = await conn.getFile(buffer)
573
+ let { res, data: file } = type
574
+ if (res && res.status !== 200 || file.length <= 65536) {
575
+ try { throw { json: JSON.parse(file.toString()) } }
576
+ catch (e) { if (e.json) throw e.json }
577
+ }
578
+ const buttons = [
579
+ { buttonId: id1, buttonText: { displayText: button1 }, type: 1 }
580
+ ]
581
+
582
+ const buttonMessage = {
583
+ image: file,
584
+ fileLength: 887890909999999,
585
+ caption: contentText,
586
+ footer: footerText,
587
+ mentions: await conn.parseMention(contentText + footerText),
588
+ ...options,
589
+ buttons: buttons,
590
+ headerType: 4
591
+ }
592
+
593
+ return await conn.sendMessage(jid, buttonMessage, { quoted, ephemeralExpiration: 86400, contextInfo: { mentionedJid: conn.parseMention(contentText + footerText) }, ...options })
594
+ }
595
+ conn.send2ButtonImg = async (jid, buffer, contentText, footerText, button1, id1, button2, id2, quoted, options) => {
596
+ let type = await conn.getFile(buffer)
597
+ let { res, data: file } = type
598
+ if (res && res.status !== 200 || file.length <= 65536) {
599
+ try { throw { json: JSON.parse(file.toString()) } }
600
+ catch (e) { if (e.json) throw e.json }
601
+ }
602
+ const buttons = [
603
+ { buttonId: id1, buttonText: { displayText: button1 }, type: 1 },
604
+ { buttonId: id2, buttonText: { displayText: button2 }, type: 1 }
605
+ ]
606
+
607
+ const buttonMessage = {
608
+ image: file,
609
+ fileLength: 887890909999999,
610
+ caption: contentText,
611
+ footer: footerText,
612
+ mentions: await conn.parseMention(contentText + footerText),
613
+ ...options,
614
+ buttons: buttons,
615
+ headerType: 4
616
+ }
617
+
618
+ return await conn.sendMessage(jid, buttonMessage, { quoted, ephemeralExpiration: 86400, contextInfo: { mentionedJid: conn.parseMention(contentText + footerText) }, ...options })
619
+ }
620
+ conn.send3ButtonImg = async (jid, buffer, contentText, footerText, button1, id1, button2, id2, button3, id3, quoted, options) => {
621
+ let type = await conn.getFile(buffer)
622
+ let { res, data: file } = type
623
+ if (res && res.status !== 200 || file.length <= 65536) {
624
+ try { throw { json: JSON.parse(file.toString()) } }
625
+ catch (e) { if (e.json) throw e.json }
626
+ }
627
+ const buttons = [
628
+ { buttonId: id1, buttonText: { displayText: button1 }, type: 1 },
629
+ { buttonId: id2, buttonText: { displayText: button2 }, type: 1 },
630
+ { buttonId: id3, buttonText: { displayText: button3 }, type: 1 }
631
+ ]
632
+
633
+ const buttonMessage = {
634
+ image: file,
635
+ fileLength: 887890909999999,
636
+ caption: contentText,
637
+ footer: footerText,
638
+ mentions: await conn.parseMention(contentText + footerText),
639
+ ...options,
640
+ buttons: buttons,
641
+ headerType: 4
642
+ }
643
+
644
+ return await conn.sendMessage(jid, buttonMessage, { quoted, ephemeralExpiration: 86400, contextInfo: { mentionedJid: conn.parseMention(contentText + footerText) }, ...options })
645
+ }
646
+
647
+ conn.sendH3Button = async (jid, content, displayText, link, displayCall, number, quickReplyText, id, quickReplyText2, id2, quickReplyText3, id3, quoted) => {
648
+ let template = generateWAMessageFromContent(jid, proto.Message.fromObject({
649
+ templateMessage: {
650
+ hydratedTemplate: {
651
+ hydratedContentText: content,
652
+ hydratedButtons: [{
653
+ urlButton: {
654
+ displayText: displayText,
655
+ url: link
656
+ }
657
+ }, {
658
+ callButton: {
659
+ displayText: displayCall,
660
+ phoneNumber: number
661
+ }
662
+ },
663
+ {
664
+ quickReplyButton: {
665
+ displayText: quickReplyText,
666
+ id: id,
667
+ }
668
+
669
+ },
670
+ {
671
+ quickReplyButton: {
672
+ displayText: quickReplyText2,
673
+ id: id2,
674
+ }
675
+ },
676
+ {
677
+ quickReplyButton: {
678
+ displayText: quickReplyText3,
679
+ id: id3,
680
+ }
681
+ }]
682
+ }
683
+ }
684
+ }), { userJid: conn.user.jid, quoted: quoted});
685
+ return await conn.relayMessage(
686
+ jid,
687
+ template.message,
688
+ { messageId: template.key.id }
689
+ )
690
+ }
691
+
692
+ conn.cMod = (jid, message, text = '', sender = conn.user.jid, options = {}) => {
693
+ let copy = message.toJSON()
694
+ let mtype = Object.keys(copy.message)[0]
695
+ let isEphemeral = false // mtype === 'ephemeralMessage'
696
+ if (isEphemeral) {
697
+ mtype = Object.keys(copy.message.ephemeralMessage.message)[0]
698
+ }
699
+ let msg = isEphemeral ? copy.message.ephemeralMessage.message : copy.message
700
+ let content = msg[mtype]
701
+ if (typeof content === 'string') msg[mtype] = text || content
702
+ else if (content.caption) content.caption = text || content.caption
703
+ else if (content.text) content.text = text || content.text
704
+ if (typeof content !== 'string') msg[mtype] = { ...content, ...options }
705
+ if (copy.participant) sender = copy.participant = sender || copy.participant
706
+ else if (copy.key.participant) sender = copy.key.participant = sender || copy.key.participant
707
+ if (copy.key.remoteJid.includes('@s.whatsapp.net')) sender = sender || copy.key.remoteJid
708
+ else if (copy.key.remoteJid.includes('@broadcast')) sender = sender || copy.key.remoteJid
709
+ copy.key.remoteJid = jid
710
+ copy.key.fromMe = areJidsSameUser(sender, conn.user.id) || false
711
+ return proto.WebMessageInfo.fromObject(copy)
712
+ }
713
+ conn.sendHButtonLoc = async (jid, buffer, content, footer, distek, link1, quick1, id1,quoted) => {
714
+ let template = generateWAMessageFromContent(jid, proto.Message.fromObject({
715
+ templateMessage: {
716
+ hydratedTemplate: {
717
+ hydratedContentText: content,
718
+ mentions: conn.parseMention(content + footer),
719
+ locationMessage: {
720
+ jpegThumbnail: buffer },
721
+ hydratedFooterText: footer,
722
+ mentions: conn.parseMention(content + footer),
723
+ hydratedButtons: [{
724
+ urlButton: {
725
+ displayText: distek,
726
+ url: link1
727
+ }
728
+ }, {
729
+ quickReplyButton: {
730
+ displayText:quick1,
731
+ id: id1
732
+ }
733
+ }], mentions: conn.parseMention(content + footer)
734
+ }
735
+ }
736
+ }), { userJid: conn.user.jid, quoted: quoted, mentions: conn.parseMention(content + footer)});
737
+ return await conn.relayMessage(
738
+ jid,
739
+ template.message,
740
+ { messageId: template.key.id }
741
+ )
742
+ }
743
+
744
+ conn.sendHButt = async (jid, content, distek, link, discall, number, retek, id,quoted) => {
745
+ let template = generateWAMessageFromContent(jid, proto.Message.fromObject({
746
+ templateMessage: {
747
+ hydratedTemplate: {
748
+ hydratedContentText: content,
749
+ hydratedButtons: [{
750
+ urlButton: {
751
+ displayText: distek,
752
+ url: link
753
+ }
754
+ }, {
755
+ callButton: {
756
+ displayText: discall,
757
+ phoneNumber: number
758
+ }
759
+ },
760
+ {
761
+ quickReplyButton: {
762
+ displayText:retek,
763
+ id: id
764
+ }
765
+ }
766
+ ]
767
+ }
768
+ }
769
+ }), { userJid: conn.user.jid, quoted: quoted});
770
+ return await conn.relayMessage(
771
+ jid,
772
+ template.message,
773
+ { messageId: template.key.id }
774
+ )
775
+ }
776
+ conn.sendButtonLoc= async (jid, buffer, content, footer, button1, row1, quoted, options = {}) => {
777
+ let buttons = [{buttonId: row1, buttonText: {displayText: button1}, type: 1}]
778
+ let buttonMessage = {
779
+ location: { jpegThumbnail: buffer },
780
+ caption: content,
781
+ footer: footer,
782
+ buttons: buttons,
783
+ headerType: 6
784
+ }
785
+ return await conn.sendMessage(jid, buttonMessage, {
786
+ quoted,
787
+ upload: conn.waUploadToServer,
788
+ ...options
789
+ })
790
+ }
791
+ conn.send2ButtonLoc= async (jid, buffer, content, footer, button1, row1, button2, row2, quoted, options = {}) => {
792
+ let buttons = [{buttonId: row1, buttonText: {displayText: button1}, type: 1},
793
+ { buttonId: row2, buttonText: { displayText: button2 }, type: 1 }]
794
+ let buttonMessage = {
795
+ location: { jpegThumbnail: buffer },
796
+ caption: content,
797
+ footer: footer,
798
+ buttons: buttons,
799
+ headerType: 6
800
+ }
801
+ return await conn.sendMessage(jid, buttonMessage, {
802
+ quoted,
803
+ upload: conn.waUploadToServer,
804
+ ...options
805
+ })
806
+ }
807
+ conn.send3ButtonLoc= async (jid, buffer, content, footer, button1, row1, button2, row2, quoted, options = {}) => {
808
+ let buttons = [{buttonId: row1, buttonText: {displayText: button1}, type: 1},
809
+ { buttonId: row2, buttonText: { displayText: button2 }, type: 1 },
810
+ { buttonId: row3, buttonText: { displayText: button3 }, type: 1 }
811
+ ]
812
+ let buttonMessage = {
813
+ location: { jpegThumbnail: buffer },
814
+ caption: content,
815
+ footer: footer,
816
+ buttons: buttons,
817
+ headerType: 6
818
+ }
819
+ return await conn.sendMessage(jid, buttonMessage, {
820
+ quoted,
821
+ upload: conn.waUploadToServer,
822
+ ...options
823
+ })
824
+ }
825
+ /**
826
+ * send Button Vid
827
+ * @param {String} jid
828
+ * @param {String} contentText
829
+ * @param {String} footer
830
+ * @param {Buffer|String} buffer
831
+ * @param {String} buttons1
832
+ * @param {String} row1
833
+ * @param {Object} quoted
834
+ * @param {Object} options
835
+ */
836
+ conn.sendButtonVid = async (jid, buffer, contentText, footerText, button1, id1, quoted, options) => {
837
+ let type = await conn.getFile(buffer)
838
+ let { res, data: file } = type
839
+ if (res && res.status !== 200 || file.length <= 65536) {
840
+ try { throw { json: JSON.parse(file.toString()) } }
841
+ catch (e) { if (e.json) throw e.json }
842
+ }
843
+ let buttons = [
844
+ { buttonId: id1, buttonText: { displayText: button1 }, type: 1 }
845
+ ]
846
+ const buttonMessage = {
847
+ video: file,
848
+ fileLength: 887890909999999,
849
+ caption: contentText,
850
+ footer: footerText,
851
+ mentions: await conn.parseMention(contentText),
852
+ ...options,
853
+ buttons: buttons,
854
+ headerType: 4
855
+ }
856
+ return await conn.sendMessage(jid, buttonMessage, {
857
+ quoted,
858
+ ephemeralExpiration: 86400,
859
+ ...options
860
+ })
861
+ }
862
+ /**
863
+ * cMod
864
+ * @param {String} jid
865
+ * @param {*} message
866
+ * @param {String} text
867
+ * @param {String} sender
868
+ * @param {*} options
869
+ * @returns
870
+ */
871
+
872
+ conn.cMod = async (jid, message, text = '', sender = conn.user.jid, options = {}) => {
873
+ if (options.mentions && !Array.isArray(options.mentions)) options.mentions = [options.mentions]
874
+ let copy = message.toJSON()
875
+ delete copy.message.messageContextInfo
876
+ delete copy.message.senderKeyDistributionMessage
877
+ let mtype = Object.keys(copy.message)[0]
878
+ let msg = copy.message
879
+ let content = msg[mtype]
880
+ if (typeof content === 'string') msg[mtype] = text || content
881
+ else if (content.caption) content.caption = text || content.caption
882
+ else if (content.text) content.text = text || content.text
883
+ if (typeof content !== 'string') {
884
+ msg[mtype] = { ...content, ...options }
885
+ msg[mtype].contextInfo = {
886
+ ...(content.contextInfo || {}),
887
+ mentionedJid: options.mentions || content.contextInfo?.mentionedJid || []
888
+ }
889
+ }
890
+ if (copy.participant) sender = copy.participant = sender || copy.participant
891
+ else if (copy.key.participant) sender = copy.key.participant = sender || copy.key.participant
892
+ if (copy.key.remoteJid.includes('@s.whatsapp.net')) sender = sender || copy.key.remoteJid
893
+ else if (copy.key.remoteJid.includes('@broadcast')) sender = sender || copy.key.remoteJid
894
+ copy.key.remoteJid = jid
895
+ copy.key.fromMe = areJidsSameUser(sender, conn.user.id) || false
896
+ return proto.WebMessageInfo.fromObject(copy)
897
+ }
898
+
899
+ /**
900
+ * cMods
901
+ * @param {String} jid
902
+ * @param {proto.WebMessageInfo} message
903
+ * @param {String} text
904
+ * @param {String} sender
905
+ * @param {*} options
906
+ * @returns
907
+ */
908
+ conn.cMods = (jid, message, text = '', sender = conn.user.jid, options = {}) => {
909
+ let copy = message.toJSON()
910
+ let mtype = Object.keys(copy.message)[0]
911
+ let isEphemeral = false // mtype === 'ephemeralMessage'
912
+ if (isEphemeral) {
913
+ mtype = Object.keys(copy.message.ephemeralMessage.message)[0]
914
+ }
915
+ let msg = isEphemeral ? copy.message.ephemeralMessage.message : copy.message
916
+ let content = msg[mtype]
917
+ if (typeof content === 'string') msg[mtype] = text || content
918
+ else if (content.caption) content.caption = text || content.caption
919
+ else if (content.text) content.text = text || content.text
920
+ if (typeof content !== 'string') msg[mtype] = { ...content, ...options }
921
+ if (copy.participant) sender = copy.participant = sender || copy.participant
922
+ else if (copy.key.participant) sender = copy.key.participant = sender || copy.key.participant
923
+ if (copy.key.remoteJid.includes('@s.whatsapp.net')) sender = sender || copy.key.remoteJid
924
+ else if (copy.key.remoteJid.includes('@broadcast')) sender = sender || copy.key.remoteJid
925
+ copy.key.remoteJid = jid
926
+ copy.key.fromMe = areJidsSameUser(sender, conn.user.id) || false
927
+ return proto.WebMessageInfo.fromObject(copy)
928
+ }
929
+
930
+
931
+
932
+ /**
933
+ * Exact Copy Forward
934
+ * @param {String} jid
935
+ * @param {proto.WebMessageInfo} message
936
+ * @param {Boolean|Number} forwardingScore
937
+ * @param {Object} options
938
+ */
939
+ conn.copyNForward = async (jid, message, forwardingScore = true, options = {}) => {
940
+ let m = generateForwardMessageContent(message, !!forwardingScore)
941
+ let mtype = Object.keys(m)[0]
942
+ if (forwardingScore && typeof forwardingScore == 'number' && forwardingScore > 1) m[mtype].contextInfo.forwardingScore += forwardingScore
943
+ m = generateWAMessageFromContent(jid, m, { ...options, userJid: conn.user.id })
944
+ await conn.relayMessage(jid, m.message, { messageId: m.key.id, additionalAttributes: { ...options } })
945
+ return m
946
+ }
947
+
948
+ /**
949
+ * Fake Replies
950
+ * @param {String} jid
951
+ * @param {String|Object} text
952
+ * @param {String} fakeJid
953
+ * @param {String} fakeText
954
+ * @param {String} fakeGroupJid
955
+ * @param {String} options
956
+ */
957
+ conn.fakeReply = async (jid, text = '', fakeJid = this.user.jid, fakeText = '', fakeGroupJid, options) => {
958
+ return conn.reply(jid, text, { key: { fromMe: areJidsSameUser(fakeJid, conn.user.id), participant: fakeJid, ...(fakeGroupJid ? { remoteJid: fakeGroupJid } : {}) }, message: { conversation: fakeText }, ...options })
959
+ }
960
+
961
+ conn.loadMessage = conn.loadMessage || (async (messageID) => {
962
+ return Object.entries(conn.chats)
963
+ .filter(([_, { messages }]) => typeof messages === 'object')
964
+ .find(([_, { messages }]) => Object.entries(messages)
965
+ .find(([k, v]) => (k === messageID || v.key?.id === messageID)))
966
+ ?.[1].messages?.[messageID]
967
+ })
968
+
969
+ /**
970
+ * Download media message
971
+ * @param {Object} m
972
+ * @param {String} type
973
+ * @param {fs.PathLike|fs.promises.FileHandle} filename
974
+ * @returns {Promise<fs.PathLike|fs.promises.FileHandle|Buffer>}
975
+ */
976
+ conn.downloadM = async (m, type, saveToFile) => {
977
+ if (!m || !(m.url || m.directPath)) return Buffer.alloc(0)
978
+ const stream = await downloadContentFromMessage(m, type)
979
+ let buffer = Buffer.from([])
980
+ for await (const chunk of stream) {
981
+ buffer = Buffer.concat([buffer, chunk])
982
+ }
983
+ if (saveToFile) var { filename } = await conn.getFile(buffer, true)
984
+ return saveToFile && fs.existsSync(filename) ? filename : buffer
985
+ }
986
+
987
+
988
+ conn.downloadAndSaveMediaMessage = async (message, filename, attachExtension = true) => {
989
+ let quoted = message.msg ? message.msg : message
990
+ let mime = (message.msg || message).mimetype || ''
991
+ let messageType = message.mtype ? message.mtype.replace(/Message/gi, '') : mime.split('/')[0]
992
+ const stream = await downloadContentFromMessage(quoted, messageType)
993
+ let buffer = Buffer.from([])
994
+ for await(const chunk of stream) {
995
+ buffer = Buffer.concat([buffer, chunk])
996
+ }
997
+ let type = await FileType.fromBuffer(buffer)
998
+ trueFileName = attachExtension ? (filename + '.' + type.ext) : filename
999
+ // save to file
1000
+ await fs.writeFileSync(trueFileName, buffer)
1001
+ return trueFileName
1002
+ }
1003
+
1004
+
1005
+ /**
1006
+ * parseMention(s)
1007
+ * @param {string} text
1008
+ * @returns {string[]}
1009
+ */
1010
+ conn.parseMention = (text = '') => {
1011
+ return [...text.matchAll(/@([0-9]{5,16}|0)/g)].map(v => v[1] + '@s.whatsapp.net')
1012
+ }
1013
+ /**
1014
+ * Read message
1015
+ * @param {String} jid
1016
+ * @param {String|undefined|null} participant
1017
+ * @param {String} messageID
1018
+ */
1019
+ conn.chatRead = async (jid, participant = conn.user.jid, messageID) => {
1020
+ return await conn.sendReadReceipt(jid, participant, [messageID])
1021
+ }
1022
+
1023
+ /**
1024
+ * Parses string into mentionedJid(s)
1025
+ * @param {String} text
1026
+ */
1027
+ conn.parseMention = (text = '') => {
1028
+ return [...text.matchAll(/@([0-9]{5,16}|0)/g)].map(v => v[1] + '@s.whatsapp.net')
1029
+ }
1030
+
1031
+ conn.sendTextWithMentions = async (jid, text, quoted, options = {}) => conn.sendMessage(jid, { text: text, contextInfo: { mentionedJid: [...text.matchAll(/@(\d{0,16})/g)].map(v => v[1] + '@s.whatsapp.net') }, ...options }, { quoted })
1032
+
1033
+ /**
1034
+ * Get name from jid
1035
+ * @param {String} jid
1036
+ * @param {Boolean} withoutContact
1037
+ */
1038
+ conn.getName = (jid = '', withoutContact = false) => {
1039
+ jid = conn.decodeJid(jid)
1040
+ withoutContact = this.withoutContact || withoutContact
1041
+ let v
1042
+ if (jid.endsWith('@g.us')) return new Promise(async (resolve) => {
1043
+ v = conn.chats[jid] || {}
1044
+ if (!(v.name || v.subject)) v = await conn.groupMetadata(jid) || {}
1045
+ resolve(v.name || v.subject || PhoneNumber('+' + jid.replace('@s.whatsapp.net', '')).getNumber('international'))
1046
+ })
1047
+ else v = jid === '0@s.whatsapp.net' ? {
1048
+ jid,
1049
+ vname: 'WhatsApp'
1050
+ } : areJidsSameUser(jid, conn.user.id) ?
1051
+ conn.user :
1052
+ (conn.chats[jid] || {})
1053
+ return (withoutContact ? '' : v.name) || v.subject || v.vname || v.notify || v.verifiedName || PhoneNumber('+' + jid.replace('@s.whatsapp.net', '')).getNumber('international')
1054
+ }
1055
+
1056
+ /**
1057
+ * to process MessageStubType
1058
+ * @param {proto.WebMessageInfo} m
1059
+ */
1060
+ conn.processMessageStubType = async(m) => {
1061
+ /**
1062
+ * to process MessageStubType
1063
+ * @param {import('@adiwajshing/baileys').proto.WebMessageInfo} m
1064
+ */
1065
+ if (!m.messageStubType) return
1066
+ const chat = conn.decodeJid(m.key.remoteJid || m.message?.senderKeyDistributionMessage?.groupId || '')
1067
+ if (!chat || chat === 'status@broadcast') return
1068
+ const emitGroupUpdate = (update) => {
1069
+ conn.ev.emit('groups.update', [{ id: chat, ...update }])
1070
+ }
1071
+ switch (m.messageStubType) {
1072
+ case WAMessageStubType.REVOKE:
1073
+ case WAMessageStubType.GROUP_CHANGE_INVITE_LINK:
1074
+ emitGroupUpdate({ revoke: m.messageStubParameters[0] })
1075
+ break
1076
+ case WAMessageStubType.GROUP_CHANGE_ICON:
1077
+ emitGroupUpdate({ icon: m.messageStubParameters[0] })
1078
+ break
1079
+ default: {
1080
+ console.log({
1081
+ messageStubType: m.messageStubType,
1082
+ messageStubParameters: m.messageStubParameters,
1083
+ type: WAMessageStubType[m.messageStubType]
1084
+ })
1085
+ break
1086
+ }
1087
+ }
1088
+ const isGroup = chat.endsWith('@g.us')
1089
+ if (!isGroup) return
1090
+ let chats = conn.chats[chat]
1091
+ if (!chats) chats = conn.chats[chat] = { id: chat }
1092
+ chats.isChats = true
1093
+ const metadata = await conn.groupMetadata(chat).catch(_ => null)
1094
+ if (!metadata) return
1095
+ chats.subject = metadata.subject
1096
+ chats.metadata = metadata
1097
+ }
1098
+ conn.insertAllGroup = async() => {
1099
+ const groups = await conn.groupFetchAllParticipating().catch(_ => null) || {}
1100
+ for (const group in groups) conn.chats[group] = { ...(conn.chats[group] || {}), id: group, subject: groups[group].subject, isChats: true, metadata: groups[group] }
1101
+ return conn.chats
1102
+ }
1103
+
1104
+ /*conn.processMessageStubType = async (m) => {
1105
+ if (!m.messageStubType) return
1106
+ const mtype = Object.keys(m.message || {})[0]
1107
+ const chat = conn.decodeJid(m.key.remoteJid || m.message[mtype] && m.message[mtype].groupId || '')
1108
+ const isGroup = chat.endsWith('@g.us')
1109
+ if (!isGroup) return
1110
+ let chats = conn.chats[chat]
1111
+ if (!chats) chats = conn.chats[chat] = { id: chat }
1112
+ chats.isChats = true
1113
+ const metadata = await conn.groupMetadata(chat).catch(_ => null)
1114
+ if (!metadata) return
1115
+ chats.subject = metadata.subject
1116
+ chats.metadata = metadata
1117
+ }*/
1118
+
1119
+ /**
1120
+ * pushMessage
1121
+ * @param {proto.WebMessageInfo[]} m
1122
+ */
1123
+ conn.pushMessage = async(m) => {
1124
+ /**
1125
+ * pushMessage
1126
+ * @param {import('@adiwajshing/baileys').proto.WebMessageInfo[]} m
1127
+ */
1128
+ if (!m) return
1129
+ if (!Array.isArray(m)) m = [m]
1130
+ for (const message of m) {
1131
+ try {
1132
+ // if (!(message instanceof proto.WebMessageInfo)) continue // https://github.com/adiwajshing/Baileys/pull/696/commits/6a2cb5a4139d8eb0a75c4c4ea7ed52adc0aec20f
1133
+ if (!message) continue
1134
+ if (message.messageStubType && message.messageStubType != WAMessageStubType.CIPHERTEXT) conn.processMessageStubType(message).catch(console.error)
1135
+ const _mtype = Object.keys(message.message || {})
1136
+ const mtype = (!['senderKeyDistributionMessage', 'messageContextInfo'].includes(_mtype[0]) && _mtype[0]) ||
1137
+ (_mtype.length >= 3 && _mtype[1] !== 'messageContextInfo' && _mtype[1]) ||
1138
+ _mtype[_mtype.length - 1]
1139
+ const chat = conn.decodeJid(message.key.remoteJid || message.message?.senderKeyDistributionMessage?.groupId || '')
1140
+ if (message.message?.[mtype]?.contextInfo?.quotedMessage) {
1141
+ /**
1142
+ * @type {import('@adiwajshing/baileys').proto.IContextInfo}
1143
+ */
1144
+ let context = message.message[mtype].contextInfo
1145
+ let participant = conn.decodeJid(context.participant)
1146
+ const remoteJid = conn.decodeJid(context.remoteJid || participant)
1147
+ /**
1148
+ * @type {import('@adiwajshing/baileys').proto.IMessage}
1149
+ *
1150
+ */
1151
+ let quoted = message.message[mtype].contextInfo.quotedMessage
1152
+ if ((remoteJid && remoteJid !== 'status@broadcast') && quoted) {
1153
+ let qMtype = Object.keys(quoted)[0]
1154
+ if (qMtype == 'conversation') {
1155
+ quoted.extendedTextMessage = { text: quoted[qMtype] }
1156
+ delete quoted.conversation
1157
+ qMtype = 'extendedTextMessage'
1158
+ }
1159
+
1160
+ if (!quoted[qMtype].contextInfo) quoted[qMtype].contextInfo = {}
1161
+ quoted[qMtype].contextInfo.mentionedJid = context.mentionedJid || quoted[qMtype].contextInfo.mentionedJid || []
1162
+ const isGroup = remoteJid.endsWith('g.us')
1163
+ if (isGroup && !participant) participant = remoteJid
1164
+ const qM = {
1165
+ key: {
1166
+ remoteJid,
1167
+ fromMe: areJidsSameUser(conn.user.jid, remoteJid),
1168
+ id: context.stanzaId,
1169
+ participant,
1170
+ },
1171
+ message: JSON.parse(JSON.stringify(quoted)),
1172
+ ...(isGroup ? { participant } : {})
1173
+ }
1174
+ let qChats = conn.chats[participant]
1175
+ if (!qChats) qChats = conn.chats[participant] = { id: participant, isChats: !isGroup }
1176
+ if (!qChats.messages) qChats.messages = {}
1177
+ if (!qChats.messages[context.stanzaId] && !qM.key.fromMe) qChats.messages[context.stanzaId] = qM
1178
+ let qChatsMessages
1179
+ if ((qChatsMessages = Object.entries(qChats.messages)).length > 40) qChats.messages = Object.fromEntries(qChatsMessages.slice(30, qChatsMessages.length)) // maybe avoid memory leak
1180
+ }
1181
+ }
1182
+ if (!chat || chat === 'status@broadcast') continue
1183
+ const isGroup = chat.endsWith('@g.us')
1184
+ let chats = conn.chats[chat]
1185
+ if (!chats) {
1186
+ if (isGroup) await conn.insertAllGroup().catch(console.error)
1187
+ chats = conn.chats[chat] = { id: chat, isChats: true, ...(conn.chats[chat] || {}) }
1188
+ }
1189
+ let metadata, sender
1190
+ if (isGroup) {
1191
+ if (!chats.subject || !chats.metadata) {
1192
+ metadata = await conn.groupMetadata(chat).catch(_ => ({})) || {}
1193
+ if (!chats.subject) chats.subject = metadata.subject || ''
1194
+ if (!chats.metadata) chats.metadata = metadata
1195
+ }
1196
+ sender = conn.decodeJid(message.key?.fromMe && conn.user.id || message.participant || message.key?.participant || chat || '')
1197
+ if (sender !== chat) {
1198
+ let chats = conn.chats[sender]
1199
+ if (!chats) chats = conn.chats[sender] = { id: sender }
1200
+ if (!chats.name) chats.name = message.pushName || chats.name || ''
1201
+ }
1202
+ } else if (!chats.name) chats.name = message.pushName || chats.name || ''
1203
+ if (['senderKeyDistributionMessage', 'messageContextInfo'].includes(mtype)) continue
1204
+ chats.isChats = true
1205
+ if (!chats.messages) chats.messages = {}
1206
+ const fromMe = message.key.fromMe || areJidsSameUser(sender || chat, conn.user.id)
1207
+ if (!['protocolMessage'].includes(mtype) && !fromMe && message.messageStubType != WAMessageStubType.CIPHERTEXT && message.message) {
1208
+ delete message.message.messageContextInfo
1209
+ delete message.message.senderKeyDistributionMessage
1210
+ chats.messages[message.key.id] = JSON.parse(JSON.stringify(message, null, 2))
1211
+ let chatsMessages
1212
+ if ((chatsMessages = Object.entries(chats.messages)).length > 40) chats.messages = Object.fromEntries(chatsMessages.slice(30, chatsMessages.length))
1213
+ }
1214
+ } catch (e) {
1215
+ console.error(e)
1216
+ }
1217
+ }
1218
+ }
1219
+
1220
+ /*conn.pushMessage = async (m) => {
1221
+ if (!m) return
1222
+ if (!Array.isArray(m)) m = [m]
1223
+ for (const message of m) {
1224
+ try {
1225
+ // if (!(message instanceof proto.WebMessageInfo)) continue // https://github.com/adiwajshing/Baileys/pull/696/commits/6a2cb5a4139d8eb0a75c4c4ea7ed52adc0aec20f
1226
+ if (!message) continue
1227
+ if (message.messageStubType) conn.processMessageStubType(message).catch(console.error)
1228
+ let mtype = Object.keys(message.message || {})
1229
+ mtype = mtype[mtype[0] === 'messageContextInfo' && mtype.length == 2 ? 1 : 0]
1230
+ const chat = conn.decodeJid(message.key.remoteJid || message.message[mtype] && message.message[mtype].groupId || '')
1231
+ const isGroup = chat.endsWith('@g.us')
1232
+ let chats = conn.chats[chat]
1233
+ if (!chats) {
1234
+ if (isGroup) {
1235
+ const groups = await conn.groupFetchAllParticipating().catch(_ => ({}))
1236
+ for (const group in groups) conn.chats[group] = { id: group, subject: groups[group].subject, isChats: true, metadata: groups[group] }
1237
+ }
1238
+ chats = conn.chats[chat] = { id: chat, ...(conn.chats[chat] || {}) }
1239
+ }
1240
+ let metadata, sender
1241
+ if (isGroup) {
1242
+ if (!chats.subject || !chats.metadata) {
1243
+ metadata = await conn.groupMetadata(chat).catch(_ => ({})) || {}
1244
+ if (!chats.subject) chats.subject = metadata.subject || ''
1245
+ if (!chats.metadata) chats.metadata = metadata
1246
+ }
1247
+ sender = conn.decodeJid(message.fromMe && conn.user.id || message.participant || message.key.participant || chat || '')
1248
+ if (sender !== chat) {
1249
+ let chats = conn.chats[sender]
1250
+ if (!chats) chats = conn.chats[sender] = { id: sender }
1251
+ if (!chats.name) chats.name = message.pushName || chats.name || ''
1252
+ }
1253
+ } else {
1254
+ if (!chats.name) chats.name = message.pushName || chats.name || ''
1255
+ }
1256
+ if (['senderKeyDistributionMessage', 'protocolMessage'].includes(mtype)) continue
1257
+ chats.isChats = true
1258
+ const fromMe = message.key.fromMe || areJidsSameUser(chat, conn.user.id)
1259
+ if (!chats.messages) chats.messages = {}
1260
+ if (!fromMe) chats.messages[message.key.id] = JSON.parse(JSON.stringify(message, null, 2))
1261
+ } catch (e) {
1262
+ console.error(e)
1263
+ }
1264
+ }
1265
+ }*/
1266
+
1267
+ /**
1268
+ *
1269
+ * @param {...any} args
1270
+ * @returns
1271
+ */
1272
+ conn.format = (...args) => {
1273
+ return util.format(...args)
1274
+ }
1275
+
1276
+ /**
1277
+ *
1278
+ * @param {String} url
1279
+ * @param {Object} options
1280
+ * @returns
1281
+ */
1282
+ conn.getBuffer = async (url, options) => {
1283
+ try {
1284
+ options ? options : {}
1285
+ const res = await axios({
1286
+ method: "get",
1287
+ url,
1288
+ headers: {
1289
+ 'DNT': 1,
1290
+ 'Upgrade-Insecure-Request': 1
1291
+ },
1292
+ ...options,
1293
+ responseType: 'arraybuffer'
1294
+ })
1295
+ return res.data
1296
+ } catch (e) {
1297
+ console.log(`Error : ${e}`)
1298
+ }
1299
+ }
1300
+
1301
+ /**
1302
+ * Serialize Message, so it easier to manipulate
1303
+ * @param {Object} m
1304
+ */
1305
+ conn.serializeM = (m) => {
1306
+ return exports.smsg(conn, m)
1307
+ }
1308
+
1309
+ Object.defineProperty(conn, 'name', {
1310
+ value: 'WASocket',
1311
+ configurable: true,
1312
+ })
1313
+ return conn
1314
+ }
1315
+ /**
1316
+ * Serialize Message
1317
+ * @param {ReturnType<typeof makeWASocket>} conn
1318
+ * @param {proto.WebMessageInfo} m
1319
+ * @param {Boolean} hasParent
1320
+ */
1321
+ exports.smsg = (conn, m, hasParent) => {
1322
+ if (!m) return m
1323
+ let M = proto.WebMessageInfo
1324
+ m = M.fromObject(m)
1325
+ if (m.key) {
1326
+ m.id = m.key.id
1327
+ m.isBaileys = m.id && m.id.length === 22 || m.id.startsWith('3EB0') && m.id.length === 22 || false
1328
+ m.chat = conn.decodeJid(m.key.remoteJid || message.message?.senderKeyDistributionMessage?.groupId || '')
1329
+ m.isGroup = m.chat.endsWith('@g.us')
1330
+ m.sender = conn.decodeJid(m.key.fromMe && conn.user.id || m.participant || m.key.participant || m.chat || '')
1331
+ m.fromMe = m.key.fromMe || areJidsSameUser(m.sender, conn.user.id)
1332
+ }
1333
+ if (m.message) {
1334
+ let mtype = Object.keys(m.message)
1335
+ m.mtype = (!['senderKeyDistributionMessage', 'messageContextInfo'].includes(mtype[0]) && mtype[0]) || // Sometimes message in the front
1336
+ (mtype.length >= 3 && mtype[1] !== 'messageContextInfo' && mtype[1]) || // Sometimes message in midle if mtype length is greater than or equal to 3!
1337
+ mtype[mtype.length - 1] // common case
1338
+ m.msg = m.message[m.mtype]
1339
+ if (m.chat == 'status@broadcast' && ['protocolMessage', 'senderKeyDistributionMessage'].includes(m.mtype)) m.chat = (m.key.remoteJid !== 'status@broadcast' && m.key.remoteJid) || m.sender
1340
+ if (m.mtype == 'protocolMessage' && m.msg.key) {
1341
+ if (m.msg.key.remoteJid == 'status@broadcast') m.msg.key.remoteJid = m.chat
1342
+ if (!m.msg.key.participant || m.msg.key.participant == 'status_me') m.msg.key.participant = m.sender
1343
+ m.msg.key.fromMe = conn.decodeJid(m.msg.key.participant) === conn.decodeJid(conn.user.id)
1344
+ if (!m.msg.key.fromMe && m.msg.key.remoteJid === conn.decodeJid(conn.user.id)) m.msg.key.remoteJid = m.sender
1345
+ }
1346
+ m.text = m.msg.text || m.msg.caption || m.msg.contentText || m.msg || ''
1347
+ if (typeof m.text !== 'string') {
1348
+ if ([
1349
+ 'protocolMessage',
1350
+ 'messageContextInfo',
1351
+ 'stickerMessage',
1352
+ 'audioMessage',
1353
+ 'senderKeyDistributionMessage'
1354
+ ].includes(m.mtype)) m.text = ''
1355
+ else m.text = m.text.selectedDisplayText || m.text.hydratedTemplate?.hydratedContentText || m.text
1356
+ }
1357
+ m.mentionedJid = m.msg?.contextInfo?.mentionedJid?.length && m.msg.contextInfo.mentionedJid || []
1358
+ let quoted = m.quoted = m.msg?.contextInfo?.quotedMessage ? m.msg.contextInfo.quotedMessage : null
1359
+ if (m.quoted) {
1360
+ let type = Object.keys(m.quoted)[0]
1361
+ m.quoted = m.quoted[type]
1362
+ if (typeof m.quoted === 'string') m.quoted = { text: m.quoted }
1363
+ m.quoted.mtype = type
1364
+ m.quoted.id = m.msg.contextInfo.stanzaId
1365
+ m.quoted.chat = conn.decodeJid(m.msg.contextInfo.remoteJid || m.chat || m.sender)
1366
+ m.quoted.isBaileys = m.quoted.id && m.quoted.id.length === 22 || false
1367
+ m.quoted.sender = conn.decodeJid(m.msg.contextInfo.participant)
1368
+ m.quoted.fromMe = m.quoted.sender === conn.user.jid
1369
+ m.quoted.text = m.quoted.text || m.quoted.caption || m.quoted.contentText || ''
1370
+ m.quoted.name = conn.getName(m.quoted.sender)
1371
+ m.quoted.mentionedJid = m.quoted.contextInfo?.mentionedJid?.length && m.quoted.contextInfo.mentionedJid || []
1372
+ let vM = m.quoted.fakeObj = M.fromObject({
1373
+ key: {
1374
+ fromMe: m.quoted.fromMe,
1375
+ remoteJid: m.quoted.chat,
1376
+ id: m.quoted.id
1377
+ },
1378
+ message: quoted,
1379
+ ...(m.isGroup ? { participant: m.quoted.sender } : {})
1380
+ })
1381
+ m.getQuotedObj = m.getQuotedMessage = async () => {
1382
+ if (!m.quoted.id) return null
1383
+ let q = M.fromObject(await conn.loadMessage(m.quoted.id) || vM)
1384
+ return exports.smsg(conn, q)
1385
+ }
1386
+ if (m.quoted.url || m.quoted.directPath) m.quoted.download = (saveToFile = false) => conn.downloadM(m.quoted, m.quoted.mtype.replace(/message/i, ''), saveToFile)
1387
+
1388
+
1389
+ /*exports.smsg = (conn, m, hasParent) => {
1390
+ if (!m) return m
1391
+ let M = proto.WebMessageInfo
1392
+ m = M.fromObject(m)
1393
+ if (m.key) {
1394
+ m.id = m.key.id
1395
+ m.isBaileys = m.id && m.id.length === 16 || m.id.startsWith('3EB0') && m.id.length === 12 || false
1396
+ let mtype = Object.keys(m.message || {})[0]
1397
+ m.chat = conn.decodeJid(m.key.remoteJid || m.message[mtype] && m.message[mtype].groupId || '')
1398
+ m.isGroup = m.chat.endsWith('@g.us')
1399
+ m.sender = conn.decodeJid(m.fromMe && conn.user.id || m.participant || m.key.participant || m.chat || '')
1400
+ m.fromMe = m.key.fromMe || areJidsSameUser(m.sender, conn.user.id)
1401
+ }
1402
+ if (m.message) {
1403
+ let mtype = Object.keys(m.message)
1404
+ m.mtype = mtype[mtype[0] === 'messageContextInfo' && mtype.length == 2 ? 1 : 0]
1405
+ m.msg = m.message[m.mtype]
1406
+ if (m.chat == 'status@broadcast' && ['protocolMessage', 'senderKeyDistributionMessage'].includes(m.mtype)) m.chat = m.sender
1407
+ // if (m.mtype === 'ephemeralMessage') {
1408
+ // exports.smsg(conn, m.msg)
1409
+ // m.mtype = m.msg.mtype
1410
+ // m.msg = m.msg.msg
1411
+ // }
1412
+ if (m.mtype == 'protocolMessage' && m.msg.key) {
1413
+ if (m.msg.key.remoteJid == 'status@broadcast') m.msg.key.remoteJid = m.chat
1414
+ if (!m.msg.key.participant || m.msg.key.participant == 'status_me') m.msg.key.participant = m.sender
1415
+ m.msg.key.fromMe = conn.decodeJid(m.msg.key.participant) === conn.decodeJid(conn.user.id)
1416
+ if (!m.msg.key.fromMe && m.msg.key.remoteJid === conn.decodeJid(conn.user.id)) m.msg.key.remoteJid = m.sender
1417
+ }
1418
+ m.text = m.msg.text || m.msg.caption || m.msg.contentText || m.msg || ''
1419
+ m.mentionedJid = m.msg && m.msg.contextInfo && m.msg.contextInfo.mentionedJid && m.msg.contextInfo.mentionedJid.length && m.msg.contextInfo.mentionedJid || []
1420
+ let quoted = m.quoted = m.msg && m.msg.contextInfo && m.msg.contextInfo.quotedMessage ? m.msg.contextInfo.quotedMessage : null
1421
+ if (m.quoted) {
1422
+ let type = Object.keys(m.quoted)[0]
1423
+ m.quoted = m.quoted[type]
1424
+ if (typeof m.quoted === 'string') m.quoted = { text: m.quoted }
1425
+ m.quoted.mtype = type
1426
+ m.quoted.id = m.msg.contextInfo.stanzaId
1427
+ m.quoted.chat = conn.decodeJid(m.msg.contextInfo.remoteJid || m.chat || m.sender)
1428
+ m.quoted.isBaileys = m.quoted.id && m.quoted.id.length === 16 || false
1429
+ m.quoted.sender = conn.decodeJid(m.msg.contextInfo.participant)
1430
+ m.quoted.fromMe = m.quoted.sender === conn.user.jid
1431
+ m.quoted.text = m.quoted.text || m.quoted.caption || ''
1432
+ m.quoted.name = conn.getName(m.quoted.sender)
1433
+ m.quoted.mentionedJid = m.quoted.contextInfo && m.quoted.contextInfo.mentionedJid && m.quoted.contextInfo.mentionedJid.length && m.quoted.contextInfo.mentionedJid || []
1434
+ let vM = m.quoted.fakeObj = M.fromObject({
1435
+ key: {
1436
+ fromMe: m.quoted.fromMe,
1437
+ remoteJid: m.quoted.chat,
1438
+ id: m.quoted.id
1439
+ },
1440
+ message: quoted,
1441
+ ...(m.isGroup ? { participant: m.quoted.sender } : {})
1442
+ })
1443
+ m.getQuotedObj = m.getQuotedMessage = () => {
1444
+ if (!m.quoted.id) return false
1445
+ let q = M.fromObject(((conn.chats[m.quoted.chat] || {}).messages || {})[m.quoted.id])
1446
+ return exports.smsg(conn, q ? q : vM)
1447
+ }
1448
+
1449
+ if (m.quoted.url || m.quoted.directPath) m.quoted.download = (saveToFile = false) => conn.downloadM(m.quoted, m.quoted.mtype.replace(/message/i, ''), saveToFile)*/
1450
+
1451
+ /**
1452
+ * Reply to quoted message
1453
+ * @param {String|Object} text
1454
+ * @param {String|false} chatId
1455
+ * @param {Object} options
1456
+ */
1457
+ m.quoted.reply = (text, chatId, options) => conn.reply(chatId ? chatId : m.chat, text, vM, options)
1458
+
1459
+ /**
1460
+ * Copy quoted message
1461
+ */
1462
+ m.quoted.copy = () => exports.smsg(conn, M.fromObject(M.toObject(vM)))
1463
+
1464
+ /**
1465
+ * Forward quoted message
1466
+ * @param {String} jid
1467
+ * @param {Boolean} forceForward
1468
+ */
1469
+ m.quoted.forward = (jid, forceForward = false) => conn.forwardMessage(jid, vM, forceForward)
1470
+
1471
+ /**
1472
+ * Exact Forward quoted message
1473
+ * @param {String} jid
1474
+ * @param {Boolean|Number} forceForward
1475
+ * @param {Object} options
1476
+ */
1477
+ m.quoted.copyNForward = (jid, forceForward = true, options = {}) => conn.copyNForward(jid, vM, forceForward, options)
1478
+
1479
+ /**
1480
+ * Modify quoted Message
1481
+ * @param {String} jid
1482
+ * @param {String} text
1483
+ * @param {String} sender
1484
+ * @param {Object} options
1485
+ */
1486
+ m.quoted.cMod = (jid, text = '', sender = m.quoted.sender, options = {}) => conn.cMod(jid, vM, text, sender, options)
1487
+
1488
+ /**
1489
+ * Delete quoted message
1490
+ */
1491
+ m.quoted.delete = () => conn.sendMessage(m.quoted.chat, { delete: vM.key })
1492
+ }
1493
+ }
1494
+ m.name = m.pushName || conn.getName(m.sender)
1495
+ if (m.msg && m.msg.url) m.download = (saveToFile = false) => conn.downloadM(m.msg, m.mtype.replace(/message/i, ''), saveToFile)
1496
+ /**
1497
+ * Reply to this message
1498
+ * @param {String|Object} text
1499
+ * @param {String|false} chatId
1500
+ * @param {Object} options
1501
+ */
1502
+ m.reply = (text, chatId, options) => conn.reply(chatId ? chatId : m.chat, text, m, options)
1503
+
1504
+ /**
1505
+ * Copy this message
1506
+ */
1507
+ m.copy = () => exports.smsg(conn, M.fromObject(M.toObject(m)))
1508
+
1509
+ /**
1510
+ * Forward this message
1511
+ * @param {String} jid
1512
+ * @param {Boolean} forceForward
1513
+ */
1514
+ m.forward = (jid = m.chat, forceForward = false) => conn.copyNForward(jid, m, forceForward, options)
1515
+
1516
+ /**
1517
+ * Exact Forward this message
1518
+ * @param {String} jid
1519
+ * @param {Boolean} forceForward
1520
+ * @param {Object} options
1521
+ */
1522
+ m.copyNForward = (jid = m.chat, forceForward = true, options = {}) => conn.copyNForward(jid, m, forceForward, options)
1523
+
1524
+ /**
1525
+ * Modify this Message
1526
+ * @param {String} jid
1527
+ * @param {String} text
1528
+ * @param {String} sender
1529
+ * @param {Object} options
1530
+ */
1531
+ m.cMod = (jid, text = '', sender = m.sender, options = {}) => conn.cMod(jid, m, text, sender, options)
1532
+
1533
+ /**
1534
+ * Delete this message
1535
+ */
1536
+ m.delete = () => conn.sendMessage(m.chat, { delete: m.key })
1537
+
1538
+ try {
1539
+ if (m.msg && m.mtype == 'protocolMessage') conn.ev.emit('message.delete', m.msg.key)
1540
+ } catch (e) {
1541
+ console.error(e)
1542
+ }
1543
+ return m
1544
+ }
1545
+
1546
+ exports.logic = (check, inp, out) => {
1547
+ if (inp.length !== out.length) throw new Error('Input and Output must have same length')
1548
+ for (let i in inp) if (util.isDeepStrictEqual(check, inp[i])) return out[i]
1549
+ return null
1550
+ }
1551
+
1552
+ exports.protoType = () => {
1553
+ Buffer.prototype.toArrayBuffer = function toArrayBufferV2() {
1554
+ const ab = new ArrayBuffer(this.length);
1555
+ const view = new Uint8Array(ab);
1556
+ for (let i = 0; i < this.length; ++i) {
1557
+ view[i] = this[i];
1558
+ }
1559
+ return ab;
1560
+ }
1561
+ /**
1562
+ * @returns {ArrayBuffer}
1563
+ */
1564
+ Buffer.prototype.toArrayBufferV2 = function toArrayBuffer() {
1565
+ return this.buffer.slice(this.byteOffset, this.byteOffset + this.byteLength)
1566
+ }
1567
+ /**
1568
+ * @returns {Buffer}
1569
+ */
1570
+ ArrayBuffer.prototype.toBuffer = function toBuffer() {
1571
+ return Buffer.from(new Uint8Array(this))
1572
+ }
1573
+ // /**
1574
+ // * @returns {String}
1575
+ // */
1576
+ // Buffer.prototype.toUtilFormat = ArrayBuffer.prototype.toUtilFormat = Object.prototype.toUtilFormat = Array.prototype.toUtilFormat = function toUtilFormat() {
1577
+ // return util.format(this)
1578
+ // }
1579
+ Uint8Array.prototype.getFileType = ArrayBuffer.prototype.getFileType = Buffer.prototype.getFileType = async function getFileType() {
1580
+ return await fileTypeFromBuffer(this)
1581
+ }
1582
+ /**
1583
+ * @returns {Boolean}
1584
+ */
1585
+ String.prototype.isNumber = Number.prototype.isNumber = isNumber
1586
+ /**
1587
+ *
1588
+ * @returns {String}
1589
+ */
1590
+ String.prototype.capitalize = function capitalize() {
1591
+ return this.charAt(0).toUpperCase() + this.slice(1, this.length)
1592
+ }
1593
+ /**
1594
+ * @returns {String}
1595
+ */
1596
+ String.prototype.capitalizeV2 = function capitalizeV2() {
1597
+ const str = this.split(' ')
1598
+ return str.map(v => v.capitalize()).join(' ')
1599
+ }
1600
+ String.prototype.decodeJid = function decodeJid() {
1601
+ if (/:\d+@/gi.test(this)) {
1602
+ const decode = jidDecode(this) || {}
1603
+ return (decode.user && decode.server && decode.user + '@' + decode.server || this).trim()
1604
+ } else return this.trim()
1605
+ }
1606
+ /**
1607
+ * number must be milliseconds
1608
+ * @returns {string}
1609
+ */
1610
+ Number.prototype.toTimeString = function toTimeString() {
1611
+ // const milliseconds = this % 1000
1612
+ const seconds = Math.floor((this / 1000) % 60)
1613
+ const minutes = Math.floor((this / (60 * 1000)) % 60)
1614
+ const hours = Math.floor((this / (60 * 60 * 1000)) % 24)
1615
+ const days = Math.floor((this / (24 * 60 * 60 * 1000)))
1616
+ return (
1617
+ (days ? `${days} day(s) ` : '') +
1618
+ (hours ? `${hours} hour(s) ` : '') +
1619
+ (minutes ? `${minutes} minute(s) ` : '') +
1620
+ (seconds ? `${seconds} second(s)` : '')
1621
+ ).trim()
1622
+ }
1623
+ Number.prototype.getRandom = String.prototype.getRandom = Array.prototype.getRandom = getRandom
1624
+ }
1625
+
1626
+ function isNumber() {
1627
+ const int = parseInt(this)
1628
+ return typeof int === 'number' && !isNaN(int)
1629
+ }
1630
+
1631
+ function getRandom() {
1632
+ if (Array.isArray(this) || this instanceof String) return this[Math.floor(Math.random() * this.length)]
1633
+ return Math.floor(Math.random() * this)
1634
+ }
1635
+
1636
+ function rand(isi) {
1637
+ return isi[Math.floor(Math.random() * isi.length)]
1638
+ }
lib/sticker.js ADDED
@@ -0,0 +1,209 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const fs = require('fs')
2
+ const path = require('path')
3
+ const crypto = require('crypto')
4
+ const fetch = require('node-fetch')
5
+ const { ffmpeg } = require('./converter')
6
+ const { spawn } = require('child_process')
7
+ const uploadFile = require('./uploadFile')
8
+ const { fromBuffer } = require('file-type')
9
+ const uploadImage = require('./uploadImage')
10
+
11
+ const tmp = path.join(__dirname, '../tmp')
12
+ /**
13
+ * Image to Sticker
14
+ * @param {Buffer} img Image Buffer
15
+ * @param {String} url Image URL
16
+ */
17
+ function sticker2(img, url) {
18
+ return new Promise(async (resolve, reject) => {
19
+ try {
20
+ if (url) {
21
+ let res = await fetch(url)
22
+ if (res.status !== 200) throw await res.text()
23
+ img = await res.buffer()
24
+ }
25
+ let inp = path.join(tmp, +new Date + '.jpeg')
26
+ await fs.promises.writeFile(inp, img)
27
+ let ff = spawn('ffmpeg', [
28
+ '-y',
29
+ '-i', inp,
30
+ '-vf', 'scale=512:512:flags=lanczos:force_original_aspect_ratio=decrease,format=rgba,pad=512:512:(ow-iw)/2:(oh-ih)/2:color=#00000000,setsar=1',
31
+ '-f', 'png',
32
+ '-'
33
+ ])
34
+ ff.on('error', reject)
35
+ ff.on('close', async () => {
36
+ await fs.promises.unlink(inp)
37
+ })
38
+ let bufs = []
39
+ const [_spawnprocess, ..._spawnargs] = [...(module.exports.support.gm ? ['gm'] : module.exports.magick ? ['magick'] : []), 'convert', 'png:-', 'webp:-']
40
+ let im = spawn(_spawnprocess, _spawnargs)
41
+ im.on('error', e => conn.reply(m.chat, util.format(e), m))
42
+ im.stdout.on('data', chunk => bufs.push(chunk))
43
+ ff.stdout.pipe(im.stdin)
44
+ im.on('exit', () => {
45
+ resolve(Buffer.concat(bufs))
46
+ })
47
+ } catch (e) {
48
+ reject(e)
49
+ }
50
+ })
51
+ }
52
+
53
+ async function canvas(code, type = 'png', quality = 0.92) {
54
+ let res = await fetch('https://nurutomo.herokuapp.com/api/canvas?' + queryURL({
55
+ type,
56
+ quality
57
+ }), {
58
+ method: 'POST',
59
+ headers: {
60
+ 'Content-Type': 'text/plain',
61
+ 'Content-Length': code.length
62
+ },
63
+ body: code
64
+ })
65
+ let image = await res.buffer()
66
+ return image
67
+ }
68
+
69
+ function queryURL(queries) {
70
+ return new URLSearchParams(Object.entries(queries))
71
+ }
72
+
73
+ /**
74
+ * Image to Sticker
75
+ * @param {Buffer} img Image Buffer
76
+ * @param {String} url Image URL
77
+ */
78
+ async function sticker1(img, url) {
79
+ url = url ? url : await uploadImage(img)
80
+ let {
81
+ mime
82
+ } = url ? { mime: 'image/jpeg' } : await fromBuffer(img)
83
+ let sc = `let im = await loadImg('data:${mime};base64,'+(await window.loadToDataURI('${url}')))
84
+ c.width = c.height = 512
85
+ let max = Math.max(im.width, im.height)
86
+ let w = 512 * im.width / max
87
+ let h = 512 * im.height / max
88
+ ctx.drawImage(im, 256 - w / 2, 256 - h / 2, w, h)
89
+ `
90
+ return await canvas(sc, 'webp')
91
+ }
92
+
93
+ /**
94
+ * Image/Video to Sticker
95
+ * @param {Buffer} img Image/Video Buffer
96
+ * @param {String} url Image/Video URL
97
+ * @param {String} packname EXIF Packname
98
+ * @param {String} author EXIF Author
99
+ */
100
+ async function sticker3(img, url, packname, author) {
101
+ url = url ? url : await uploadFile(img)
102
+ let res = await fetch('https://api.xteam.xyz/sticker/wm?' + new URLSearchParams(Object.entries({
103
+ url,
104
+ packname,
105
+ author
106
+ })))
107
+ return await res.buffer()
108
+ }
109
+
110
+ /**
111
+ * Image to Sticker
112
+ * @param {Buffer} img Image/Video Buffer
113
+ * @param {String} url Image/Video URL
114
+ */
115
+ async function sticker4(img, url) {
116
+ if (url) {
117
+ let res = await fetch(url)
118
+ if (res.status !== 200) throw await res.text()
119
+ img = await res.buffer()
120
+ }
121
+ return await ffmpeg(img, [
122
+ '-vf', 'scale=512:512:flags=lanczos:force_original_aspect_ratio=decrease,format=rgba,pad=512:512:(ow-iw)/2:(oh-ih)/2:color=#00000000,setsar=1'
123
+ ], 'jpeg', 'webp')
124
+ }
125
+
126
+
127
+ async function sticker5(img, url, packname, author, categories = ['']) {
128
+ const WSF = require('wa-sticker-formatter')
129
+ const stickerMetadata = {
130
+ type: 'full',
131
+ pack: packname,
132
+ author,
133
+ categories,
134
+ }
135
+ return await new WSF.Sticker(img ? img : url, stickerMetadata).build()
136
+ }
137
+
138
+
139
+ /**
140
+ * Add WhatsApp JSON Exif Metadata
141
+ * Taken from https://github.com/pedroslopez/whatsapp-web.js/pull/527/files
142
+ * @param {Buffer} webpSticker
143
+ * @param {String} packname
144
+ * @param {String} author
145
+ * @param {String} categories
146
+ * @param {Object} extra
147
+ * @returns
148
+ */
149
+ async function addExif(webpSticker, packname, author, categories = [''], extra = {}) {
150
+ const webp = require('node-webpmux') // Optional Feature
151
+ const img = new webp.Image();
152
+ const stickerPackId = crypto.randomBytes(32).toString('hex');
153
+ const json = { 'sticker-pack-id': stickerPackId, 'sticker-pack-name': packname, 'sticker-pack-publisher': author, 'emojis': categories, ...extra };
154
+ let exifAttr = Buffer.from([0x49, 0x49, 0x2A, 0x00, 0x08, 0x00, 0x00, 0x00, 0x01, 0x00, 0x41, 0x57, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x16, 0x00, 0x00, 0x00]);
155
+ let jsonBuffer = Buffer.from(JSON.stringify(json), 'utf8');
156
+ let exif = Buffer.concat([exifAttr, jsonBuffer]);
157
+ exif.writeUIntLE(jsonBuffer.length, 14, 4);
158
+ await img.loadBuffer(webpSticker)
159
+ img.exif = exif
160
+ return await img.saveBuffer()
161
+ }
162
+
163
+ module.exports = {
164
+ /**
165
+ * Image/Video to Sticker
166
+ * @param {Buffer} img Image/Video Buffer
167
+ * @param {String} url Image/Video URL
168
+ * @param {...String}
169
+ */
170
+ async sticker(img, url, ...args) {
171
+ let lastError
172
+ for (let func of [
173
+ sticker3, // sticker5,
174
+ this.support.ffmpeg && this.support.ffmpegWebp && sticker4,
175
+ this.support.ffmpeg && (this.support.convert || this.support.magick || this.support.gm) && sticker2,
176
+ sticker1
177
+ ].filter(f => f)) {
178
+ try {
179
+ let stiker = await func(img, url, ...args)
180
+ if (stiker.includes('RIFF')) {
181
+ try {
182
+ return await addExif(stiker, ...args)
183
+ } catch (e) {
184
+ return stiker
185
+ }
186
+ }
187
+ throw stiker.toString()
188
+ } catch (err) {
189
+ lastError = err
190
+ }
191
+ }
192
+ return lastError
193
+ },
194
+ sticker1,
195
+ sticker2,
196
+ sticker3,
197
+ sticker4,
198
+ sticker5,
199
+ addExif,
200
+ support: {
201
+ ffmpeg: true,
202
+ ffprobe: true,
203
+ ffmpegWebp: true,
204
+ convert: true,
205
+ magick: false,
206
+ gm: false,
207
+ find: false
208
+ }
209
+ }
lib/tictactoe.d.ts ADDED
@@ -0,0 +1,15 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ export declare class TicTacToe {
2
+ /* X PlayerName */
3
+ playerX: string;
4
+ /* Y PlayerName */
5
+ playerY: string;
6
+ /* X if true, Y if false */
7
+ _currentTurn: boolean;
8
+ _x: number;
9
+ _y: number;
10
+ _turns: number;
11
+ constructor(playerX: string, playerY: string);
12
+ get board(): number;
13
+ turn(player, index: number): boolean;
14
+ turn(player, x: number, y: number): boolean;
15
+ }
lib/tictactoe.js ADDED
@@ -0,0 +1,93 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ class TicTacToe {
2
+ constructor(playerX = 'x', playerO = 'o') {
3
+ this.playerX = playerX
4
+ this.playerO = playerO
5
+ this._currentTurn = false
6
+ this._x = 0
7
+ this._o = 0
8
+ this.turns = 0
9
+ }
10
+
11
+ get board() {
12
+ return this._x | this._o
13
+ }
14
+
15
+ get currentTurn() {
16
+ return this._currentTurn ? this.playerO : this.playerX
17
+ }
18
+
19
+ get enemyTurn() {
20
+ return this._currentTurn ? this.playerX : this.playerO
21
+ }
22
+
23
+ static check(state) {
24
+ for (let combo of [7, 56, 73, 84, 146, 273, 292, 448])
25
+ if ((state & combo) === combo)
26
+ return !0
27
+ return !1
28
+ }
29
+
30
+ /**
31
+ * ```js
32
+ * TicTacToe.toBinary(1, 2) // 0b010000000
33
+ * ```
34
+ */
35
+ static toBinary(x = 0, y = 0) {
36
+ if (x < 0 || x > 2 || y < 0 || y > 2) throw new Error('invalid position')
37
+ return 1 << x + (3 * y)
38
+ }
39
+
40
+ /**
41
+ * @param player `0` is `X`, `1` is `O`
42
+ *
43
+ * - `-3` `Game Ended`
44
+ * - `-2` `Invalid`
45
+ * - `-1` `Invalid Position`
46
+ * - ` 0` `Position Occupied`
47
+ * - ` 1` `Sucess`
48
+ * @returns {-3|-2|-1|0|1}
49
+ */
50
+ turn(player = 0, x = 0, y) {
51
+ if (this.board === 511) return -3
52
+ let pos = 0
53
+ if (y == null) {
54
+ if (x < 0 || x > 8) return -1
55
+ pos = 1 << x
56
+ } else {
57
+ if (x < 0 || x > 2 || y < 0 || y > 2) return -1
58
+ pos = TicTacToe.toBinary(x, y)
59
+ }
60
+ if (this._currentTurn ^ player) return -2
61
+ if (this.board & pos) return 0
62
+ this[this._currentTurn ? '_o' : '_x'] |= pos
63
+ this._currentTurn = !this._currentTurn
64
+ this.turns++
65
+ return 1
66
+ }
67
+
68
+ /**
69
+ * @returns {('X'|'O'|1|2|3|4|5|6|7|8|9)[]}
70
+ */
71
+ static render(boardX = 0, boardO = 0) {
72
+ let x = parseInt(boardX.toString(2), 4)
73
+ let y = parseInt(boardO.toString(2), 4) * 2
74
+ return [...(x + y).toString(4).padStart(9, '0')].reverse().map((value, index) => value == 1 ? 'X' : value == 2 ? 'O' : ++index)
75
+ }
76
+
77
+ /**
78
+ * @returns {('X'|'O'|1|2|3|4|5|6|7|8|9)[]}
79
+ */
80
+ render() {
81
+ return TicTacToe.render(this._x, this._o)
82
+ }
83
+
84
+ get winner() {
85
+ let x = TicTacToe.check(this._x)
86
+ let o = TicTacToe.check(this._o)
87
+ return x ? this.playerX : o ? this.playerO : false
88
+ }
89
+ }
90
+
91
+ new TicTacToe().turn
92
+
93
+ module.exports = TicTacToe
lib/ular_tangga.js ADDED
@@ -0,0 +1,50 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ const fs = require('fs');
2
+ const Jimp = require('jimp');
3
+
4
+ // Fungsi untuk menggambar papan permainan dengan pemain
5
+ async function drawBoard(boardImageURL, user1 = null, user2 = null, user3 = null, user4 = null, stabil_x, stabil_y) {
6
+ try {
7
+ // Load gambar papan permainan dari URL
8
+ const board = await Jimp.read(boardImageURL);
9
+
10
+ // Lokasi pemain pada papan permainan
11
+ const playerPositions = [user1, user2, user3, user4].filter(pos => pos !== null && pos >= 1 && pos <= 100);
12
+
13
+ // URL gambar untuk setiap pemain
14
+ const playerImageURLs = [
15
+ "https://telegra.ph/file/30f92f923fb0484f0e4e0.png",
16
+ "https://telegra.ph/file/6e07b5f30b24baedc7822.png",
17
+ "https://telegra.ph/file/34f47137df0dc9aa9c15a.png",
18
+ "https://telegra.ph/file/860b5df98963a1f14a91c.png"
19
+ ];
20
+
21
+ // Gambar pion untuk setiap pemain pada posisi mereka
22
+ for (let i = 0; i < playerPositions.length; i++) {
23
+ const position = playerPositions[i];
24
+ const row = Math.floor((position - 1) / 10); // Mulai dari bawah
25
+ const col = (row % 2 === 0) ? (position - 1) % 10 : 9 - (position - 1) % 10;
26
+
27
+ // Posisi pion pada papan permainan
28
+ const x = col * 60 + stabil_x
29
+ const y = (9 - row) * 60 + stabil_y
30
+
31
+ // Load gambar pemain dari URL
32
+ const playerImageURL = playerImageURLs[i];
33
+ const playerImage = await Jimp.read(playerImageURL);
34
+
35
+ // Resize gambar pemain menjadi 38x38 (sesuai dengan ukuran lingkaran)
36
+ playerImage.resize(50, 50);
37
+
38
+ // Gabungkan gambar pemain dengan papan permainan
39
+ board.composite(playerImage, x - 4, y - 4, { mode: Jimp.BLEND_SOURCE_OVER });
40
+ }
41
+
42
+ // Mengembalikan buffer gambar
43
+ return await board.getBufferAsync(Jimp.MIME_PNG);
44
+ } catch (error) {
45
+ console.error('An error occurred:', error);
46
+ return null;
47
+ }
48
+ }
49
+
50
+ module.exports = { drawBoard }