whalibmob 5.29.3 → 5.29.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -5507,6 +5507,30 @@ These variables override individual fields on top of the selected profile:
5507
5507
  | `WA_DEVICE_OS_VERSION` | OS version string (e.g. `14`) |
5508
5508
  | `WA_DEVICE_BUILD` | Build fingerprint (e.g. `UP1A.231005.007`) |
5509
5509
  | `WA_DEVICE_MODEL_ID` | Model ID slug (e.g. `samsung-sm-s928b`) |
5510
+ | `WA_DEVICE_RAM` | Usable RAM in GiB, as Android reports it (e.g. `7.53`). Each named profile carries its own; set this only for a different memory variant of the same model. |
5511
+
5512
+ ### Declaring your SIM
5513
+
5514
+ Registration sends `sim_mcc` / `sim_mnc` to say which network the SIM belongs
5515
+ to. The built-in table can only name **one operator per country** — Romania is
5516
+ always Orange, Brazil always Vivo — and it cannot do better, because number
5517
+ portability broke the prefix→operator link years ago. Guessing from the number
5518
+ would be wrong more often than the table is.
5519
+
5520
+ So say which SIM is in the phone:
5521
+
5522
+ ```js
5523
+ const store = createNewStore('40712345678', { simMcc: '226', simMnc: '01' })
5524
+ ```
5525
+
5526
+ | Variable | Description |
5527
+ |---|---|
5528
+ | `WA_SIM_MCC` | Mobile country code of the SIM (e.g. `226`) |
5529
+ | `WA_SIM_MNC` | Mobile network code. **Width matters** — `10` and `010` are different networks to the server, so write it exactly as your operator does. |
5530
+
5531
+ Either half can be given on its own; the other keeps the table's value, and the
5532
+ country's language and locale are unaffected either way. Leave both unset and
5533
+ nothing changes from before.
5510
5534
 
5511
5535
  ### Version & Token Overrides
5512
5536
 
@@ -5691,6 +5715,24 @@ registered, no code is requested, and the session is never written to.
5691
5715
  the problem.** The difference is then in what the CLI reads and this tool does
5692
5716
  not — `WA_VERSION`, from `.env`. Go back to the top of this section.
5693
5717
 
5718
+ ## Support this project
5719
+
5720
+ If whalibmob saves you time, you can support its development.
5721
+
5722
+ **USDT — TRC-20 (Tron network only)**
5723
+
5724
+ ```
5725
+ TNxxWvAc5m5YS89uz5uSrbXC9EKPuS27aP
5726
+ ```
5727
+
5728
+ > [!WARNING]
5729
+ > This address is **TRC-20 on the Tron network**. Send **only USDT on TRC-20** to
5730
+ > it. USDT sent on any other network — ERC-20 (Ethereum), BEP-20 (BSC), Polygon,
5731
+ > or anything else — will be **lost and cannot be recovered**. Always double-check
5732
+ > the network in your wallet before sending, and copy the address in full.
5733
+
5734
+ The **Sponsor** button at the top of the repository leads back here.
5735
+
5694
5736
  ## License
5695
5737
 
5696
5738
  MIT
package/index.d.ts CHANGED
@@ -1228,7 +1228,17 @@ export declare function fetchWaWebVersion(): Promise<{ version: [number, number,
1228
1228
  // Stores
1229
1229
  // ────────────────────────────────────────────────────────────────────────────
1230
1230
 
1231
- export declare function createNewStore(phoneNumber: string, opts?: { name?: string }): WhalibmobStore;
1231
+ export declare function createNewStore(phoneNumber: string, opts?: {
1232
+ name?: string;
1233
+ /**
1234
+ * The MCC of the SIM actually in the phone. Without it the country table's
1235
+ * one-operator-per-country guess stands — number portability means the
1236
+ * number's prefix cannot tell you. Also settable as `WA_SIM_MCC`.
1237
+ */
1238
+ simMcc?: string;
1239
+ /** The matching MNC. Width matters: `10` and `010` are different networks. */
1240
+ simMnc?: string;
1241
+ }): WhalibmobStore;
1232
1242
  /** What the CLI uses for every new SMS session; prefer it over `createNewStore`. */
1233
1243
  export declare function initAuthCreds(phoneNumber: string, opts?: { name?: string }): WhalibmobStore;
1234
1244
  export declare function saveStore(store: WhalibmobStore, filePath: string): void;
@@ -55,9 +55,13 @@ function getDeviceConfig() {
55
55
  const profileKey = _normalise(process.env.WA_DEVICE || 'samsungs24ultra');
56
56
  const found = _ANDROID_MAP[profileKey] || null;
57
57
  if (found) {
58
- return Object.assign({}, found, business
58
+ const picked = Object.assign({}, found, business
59
59
  ? { business: true, platform: PLATFORM.ANDROID_BUSINESS }
60
60
  : { business: false });
61
+ // A named profile carries the handset's own RAM; WA_DEVICE_RAM overrides
62
+ // it for someone running the same model in a different memory variant.
63
+ if (process.env.WA_DEVICE_RAM) picked.ram = process.env.WA_DEVICE_RAM;
64
+ return picked;
61
65
  }
62
66
 
63
67
  return {
@@ -69,6 +73,9 @@ function getDeviceConfig() {
69
73
  osVersion: process.env.WA_DEVICE_OS_VERSION || '14',
70
74
  osBuildNumber: process.env.WA_DEVICE_BUILD || 'UP1A.231005.007',
71
75
  modelId: process.env.WA_DEVICE_MODEL_ID || 'SM-S928B',
76
+ // What the handset reports as usable RAM, in GiB. Registration sends it,
77
+ // and it has to belong to the handset beside it — see deviceRam().
78
+ ram: process.env.WA_DEVICE_RAM || '11.55',
72
79
  deviceModelType: 2
73
80
  };
74
81
  }
@@ -478,8 +478,32 @@ const COUNTRY_META = {
478
478
  '998': { mcc: '434', mnc: '03', lg: 'ru', lc: 'UZ' }, // Uzbekistan (UzMobile)
479
479
  };
480
480
 
481
- function getCountryMeta(cc) {
482
- return COUNTRY_META[cc] || { mcc: '000', mnc: '000', lg: 'en', lc: 'US' };
481
+ // The carrier metadata for a country calling code.
482
+ //
483
+ // The table names one operator per country — Romania is always Orange, Brazil
484
+ // always Vivo — because that is the best a table keyed by calling code can do.
485
+ // It cannot be better: number portability means the prefix stopped naming the
486
+ // operator years ago, so guessing from the number would be wrong more often
487
+ // than the table is.
488
+ //
489
+ // So the caller can say instead. Whoever is registering knows which SIM is in
490
+ // the phone, and sim_mcc/sim_mnc are meant to describe that SIM; WA_SIM_MCC and
491
+ // WA_SIM_MNC (or `simMcc`/`simMnc` in the options) override the guess with the
492
+ // truth. The language and locale stay with the country either way.
493
+ //
494
+ // MNC keeps whatever width it is given: 226/10 and 226/010 are different
495
+ // networks to the server, and normalising them would break one of the two.
496
+ function getCountryMeta(cc, opts) {
497
+ const base = COUNTRY_META[cc] || { mcc: '000', mnc: '000', lg: 'en', lc: 'US' };
498
+
499
+ const mcc = (opts && opts.simMcc) || process.env.WA_SIM_MCC;
500
+ const mnc = (opts && opts.simMnc) || process.env.WA_SIM_MNC;
501
+ if (!mcc && !mnc) return base;
502
+
503
+ const out = Object.assign({}, base);
504
+ if (mcc) out.mcc = String(mcc).trim();
505
+ if (mnc) out.mnc = String(mnc).trim();
506
+ return out;
483
507
  }
484
508
 
485
509
  // ---------- Phone number parsing ----------
@@ -962,18 +986,38 @@ function tryLoadAndroidMaterial(device) {
962
986
  * Silently ignoring WA_OS is how you end up watching an Android registration go
963
987
  * out under an iOS User-Agent and not knowing why.
964
988
  */
989
+ // A session's device identity, frozen for the whole registration.
990
+ //
991
+ // createNewStore captures the device when the session is created and writes it
992
+ // to disk with everything else, so a session always arrives here already
993
+ // carrying one. From that point it is frozen: /exist, /code, /register and
994
+ // every retry read this same identity, and no request can describe one handset
995
+ // while a sibling request in the same flow describes another.
996
+ //
997
+ // The bug this closes: the gate here used to be `registered || codePending`, so
998
+ // the very first /code of a session ignored the stored device and re-read it
999
+ // from the environment. /exist had already gone out as the stored device — an
1000
+ // Android/Samsung, say, loaded from the session file — and /code then went out
1001
+ // as the environment default (iOS/iPhone). One number, two phones, in one flow.
1002
+ // That is precisely the shape a "download the official app" block screen looks
1003
+ // for, and it was reproducible from the logs. See
1004
+ // test/registration-device-consistency.test.js.
1005
+ //
1006
+ // WA_OS / WA_BUSINESS therefore choose the device only for a session that does
1007
+ // not have one yet — which in practice means never, since createNewStore always
1008
+ // sets it. To change the platform of an existing session, start it over: delete
1009
+ // the session file, and the next createNewStore picks up the current WA_OS.
965
1010
  function deviceForRegistration(store, opts) {
966
1011
  const env = getDeviceConfig();
967
1012
  const stored = store && store.device;
968
- const settled = !!(store && (store.registered || store.codePending));
969
- if (!settled || !stored) return env;
1013
+ if (!stored || !stored.os) return env;
970
1014
 
971
1015
  const say = (opts && opts.onProgress) || (m => _whaDbg('[DBG] REG ' + m));
972
1016
 
973
1017
  if (stored.os !== env.os) {
974
1018
  say('note: this session was started as ' + stored.os + ', so it stays ' + stored.os +
975
- ' — WA_OS=' + env.os + ' does not apply to a number that is already part-way ' +
976
- 'through registering. Delete the session file to start it over as ' + env.os + '.');
1019
+ ' — WA_OS=' + env.os + ' does not apply to a number that already has a ' +
1020
+ 'device. Delete the session file to start it over as ' + env.os + '.');
977
1021
  }
978
1022
 
979
1023
  // The same rule for the variant: an account is created as Business or as
@@ -983,13 +1027,36 @@ function deviceForRegistration(store, opts) {
983
1027
  if (!!stored.business !== !!env.business) {
984
1028
  say('note: this session was started as ' + (stored.business ? 'Business' : 'consumer') +
985
1029
  ', so it stays that — WA_BUSINESS=' + (env.business ? '1' : '0') +
986
- ' does not apply to a number that is already part-way through registering. ' +
1030
+ ' does not apply to a number that already has a device. ' +
987
1031
  'Delete the session file to start it over.');
988
1032
  }
989
1033
 
990
1034
  return stored;
991
1035
  }
992
1036
 
1037
+ // The device identity a request is about to go out with, logged so /exist and
1038
+ // /code can be compared side by side. Gated behind the debug channel — it costs
1039
+ // nothing when debug is off, and when a registration misbehaves it is the first
1040
+ // thing worth seeing. The User-Agent is built the same way the real request
1041
+ // builds it, so what this prints is what actually goes on the wire.
1042
+ function logDeviceIdentity(tag, store, waVersion) {
1043
+ const stored = store && store.device;
1044
+ const d = stored || getDeviceConfig();
1045
+ const ver = waVersion || (store && store.version) || '';
1046
+ let ua = '';
1047
+ try { ua = registrationHeaders(d, ver)['User-Agent']; } catch (_) {}
1048
+ _whaDbg('[DBG] DEVICE_IDENTITY ' + tag +
1049
+ ' os=' + d.os +
1050
+ ' osVersion=' + d.osVersion +
1051
+ ' manufacturer=' + (d.manufacturer || '-') +
1052
+ ' model=' + (d.model || d.modelId || '-') +
1053
+ ' modelId=' + (d.modelId || '-') +
1054
+ ' business=' + !!d.business +
1055
+ ' waVersion=' + (ver || '-') +
1056
+ ' source=' + (stored ? 'store.device (frozen)' : 'getDeviceConfig() (env/default)') +
1057
+ ' ua="' + ua + '"');
1058
+ }
1059
+
993
1060
  /**
994
1061
  * Have the Android token material ready, fetching the APK if it is not.
995
1062
  *
@@ -1201,6 +1268,57 @@ function waitHint(response, method) {
1201
1268
  return retry > 0 ? retry : null;
1202
1269
  }
1203
1270
 
1271
+ // ---------- device_ram ----------
1272
+ //
1273
+ // What the handset reports as usable RAM, in GiB, from
1274
+ // ActivityManager.MemoryInfo.totalMem — which is always below the nominal
1275
+ // figure on the box, because the kernel, the GPU and the secure world reserve a
1276
+ // slice before Android ever sees it. A 12 GB phone reports around 11.5.
1277
+ //
1278
+ // This was the constant 3.57 on every request, while the same payload declared
1279
+ // a Galaxy S24 Ultra beside it. There is no such handset: the S24 Ultra ships
1280
+ // with 12 GB and no variant of it has ever had 3.57. Two fields of one request
1281
+ // describing two different phones is not a fingerprint worth defending — it is
1282
+ // simply wrong, in the way a wrong `os_version` would be. It now comes off the
1283
+ // declared profile, so whichever handset the caller says they are on, the
1284
+ // memory belongs to it.
1285
+ const DEFAULT_DEVICE_RAM = '5.62';
1286
+
1287
+ function deviceRam(device) {
1288
+ const ram = device && device.ram;
1289
+ if (ram == null) return DEFAULT_DEVICE_RAM;
1290
+ const n = Number(ram);
1291
+ // Two decimals, the way the client formats it.
1292
+ return Number.isFinite(n) && n > 0 ? n.toFixed(2) : DEFAULT_DEVICE_RAM;
1293
+ }
1294
+
1295
+ // ---------- pid ----------
1296
+ //
1297
+ // The process id of the app making the request.
1298
+ //
1299
+ // This sent `process.pid` — the Node process. Inside a container that is 1, and
1300
+ // pid 1 on Android is `init`; no application process is ever 1. Elsewhere it is
1301
+ // whatever the host happened to hand out, which is as likely to be 7 as 24000.
1302
+ //
1303
+ // Android hands out pids from a counter that starts near 300 and wraps at
1304
+ // /proc/sys/kernel/pid_max, 32768 by default, so an app launched on a phone
1305
+ // that has been up any length of time lands well inside that range. One is
1306
+ // derived per store here, from the same identity material everything else in
1307
+ // the payload comes from — deterministic on purpose, because /exist, /code and
1308
+ // /register are three requests from one running app and a process does not
1309
+ // change its pid between them. Restoring a saved session keeps the pid it had,
1310
+ // for the same reason.
1311
+ function getAppPid(store) {
1312
+ if (store._appPid) return store._appPid;
1313
+ const seed = (store.identityId && Buffer.isBuffer(store.identityId))
1314
+ ? store.identityId
1315
+ : Buffer.from(String(store.phoneNumber || ''), 'utf8');
1316
+ const h = crypto.createHash('sha256').update(seed).update('pid').digest();
1317
+ // 1024..32767 — clear of the kernel and early-boot range, inside pid_max.
1318
+ store._appPid = String(1024 + (h.readUInt32BE(0) % (32768 - 1024)));
1319
+ return store._appPid;
1320
+ }
1321
+
1204
1322
  function buildClientMetrics(attempt) {
1205
1323
  const json = '{"attempts":' + (attempt || 1)
1206
1324
  + ',"app_campaign_download_source":"google-play|unknown"'
@@ -1250,9 +1368,9 @@ function getRequestVerificationCodeParameters(store, method, meta, device, attem
1250
1368
  'advertising_id', store.advertisingId || '',
1251
1369
  'hasinrc', '1',
1252
1370
  'roaming_type', '0',
1253
- 'device_ram', '3.57',
1371
+ 'device_ram', deviceRam(device),
1254
1372
  'education_screen_displayed', 'true',
1255
- 'pid', String(process.pid),
1373
+ 'pid', getAppPid(store),
1256
1374
  'cellular_strength', '5',
1257
1375
  'backup_token', store.backupToken ? toUrlHex(store.backupToken) : '',
1258
1376
  'tos_version', '5',
@@ -1354,7 +1472,7 @@ function buildVerifiedNameCertificate(store, device) {
1354
1472
 
1355
1473
  async function buildPayload(store, waVersion, useToken, extraPairs) {
1356
1474
  const { cc, national } = parsePhone(store.phoneNumber);
1357
- const meta = getCountryMeta(cc);
1475
+ const meta = getCountryMeta(cc, store);
1358
1476
  const device = store.device || getDeviceConfig();
1359
1477
  const token = useToken ? computeToken(waVersion, national, device) : null;
1360
1478
  // Android formats fdid lowercase, iOS uppercase (matches the native clients).
@@ -1826,7 +1944,7 @@ async function checkNumberStatus(phoneNumber) {
1826
1944
  const store = createNewStore(phoneNumber);
1827
1945
  const waVersion = await fetchWaVersion(_device);
1828
1946
  const { cc } = parsePhone(phoneNumber);
1829
- const meta = getCountryMeta(cc);
1947
+ const meta = getCountryMeta(cc, store);
1830
1948
 
1831
1949
  function hasBlock(r) {
1832
1950
  return r && !!r.custom_block_screen;
@@ -1908,6 +2026,7 @@ async function assertRegistrationKeys(store, waVersion) {
1908
2026
 
1909
2027
  for (let attempt = 0; attempt < 2; attempt++) {
1910
2028
  try {
2029
+ logDeviceIdentity('before /exist', store, waVersion);
1911
2030
  const result = await sendRequest('/exist', store, waVersion, false, null);
1912
2031
  // reason === 'incorrect' → keys not found → fresh
1913
2032
  if (result && result.reason === 'incorrect') {
@@ -1988,7 +2107,7 @@ async function requestSmsCode(store, method, opts) {
1988
2107
 
1989
2108
  // Derive real MCC/MNC from the phone number being registered.
1990
2109
  const { cc: _regCc } = parsePhone(store.phoneNumber);
1991
- const _regMeta = getCountryMeta(_regCc);
2110
+ const _regMeta = getCountryMeta(_regCc, store);
1992
2111
 
1993
2112
  async function _tryMethod(m) {
1994
2113
  // Retry loop:
@@ -2012,6 +2131,7 @@ async function requestSmsCode(store, method, opts) {
2012
2131
  const verifyScreen = currentVerifyScreen(store);
2013
2132
  await sendFunnelLog(store, waVersion, verifyScreen, 'request_code', 'request_code_attempt');
2014
2133
 
2134
+ logDeviceIdentity('before /code', store, waVersion);
2015
2135
  const result = await sendRequest('/code', store, waVersion, true, extra);
2016
2136
 
2017
2137
  const status = result.status;
package/lib/Store.js CHANGED
@@ -113,6 +113,12 @@ function createNewStore(phoneNumber, opts) {
113
113
  registered: false,
114
114
  codePending: false, // true after /code request, cleared on successful /register
115
115
  name: normalizePushName(opts.name) || 'User',
116
+ // Which SIM is actually in the phone. The country table can only guess one
117
+ // operator per calling code — number portability broke the prefix→operator
118
+ // link long ago — so whoever is registering can name theirs instead. Null
119
+ // leaves the table's guess in place. See getCountryMeta in Registration.js.
120
+ simMcc: opts.simMcc ? String(opts.simMcc).trim() : null,
121
+ simMnc: opts.simMnc ? String(opts.simMnc).trim() : null,
116
122
  version,
117
123
  device,
118
124
  // ADVSignedDeviceIdentity bytes received from server <success> node.
@@ -194,6 +200,8 @@ function storeToJson(store) {
194
200
  advertisingId: store.advertisingId || null,
195
201
  backupToken: store.backupToken ? store.backupToken.toString('base64') : null,
196
202
  registered: !!store.registered,
203
+ simMcc: store.simMcc || null,
204
+ simMnc: store.simMnc || null,
197
205
  codePending: store.codePending || false,
198
206
  // Which delivery method the pending code actually went out by. The two
199
207
  // registration steps are normally separate commands, so the confirmation
@@ -246,6 +254,10 @@ function storeFromJson(obj) {
246
254
  advertisingId: obj.advertisingId || uuidv4(),
247
255
  backupToken: obj.backupToken ? Buffer.from(obj.backupToken, 'base64') : crypto.randomBytes(20),
248
256
  registered: !!obj.registered,
257
+ // Null on stores written before the SIM could be declared, which simply
258
+ // means the country table's guess stands.
259
+ simMcc: obj.simMcc || null,
260
+ simMnc: obj.simMnc || null,
249
261
  codePending: obj.codePending || false,
250
262
  codeMethod: obj.codeMethod || null,
251
263
  // Absent on stores written before push tokens existed; null simply means
package/lib/constants.js CHANGED
@@ -169,91 +169,91 @@ const ANDROID_DEVICE_PROFILES = {
169
169
  os: 'android', platform: PLATFORM.ANDROID,
170
170
  model: 'Samsung Galaxy S24 Ultra', manufacturer: 'Samsung',
171
171
  osVersion: '14', osBuildNumber: 'UP1A.231005.007',
172
- modelId: 'SM-S928B', deviceModelType: 2
172
+ modelId: 'SM-S928B', deviceModelType: 2, ram: '11.55'
173
173
  },
174
174
  'samsung-s24': {
175
175
  os: 'android', platform: PLATFORM.ANDROID,
176
176
  model: 'Samsung Galaxy S24', manufacturer: 'Samsung',
177
177
  osVersion: '14', osBuildNumber: 'UP1A.231005.007',
178
- modelId: 'SM-S921B', deviceModelType: 2
178
+ modelId: 'SM-S921B', deviceModelType: 2, ram: '7.63'
179
179
  },
180
180
  'samsung-s23': {
181
181
  os: 'android', platform: PLATFORM.ANDROID,
182
182
  model: 'Samsung Galaxy S23', manufacturer: 'Samsung',
183
183
  osVersion: '14', osBuildNumber: 'UP1A.231005.007',
184
- modelId: 'SM-S911B', deviceModelType: 2
184
+ modelId: 'SM-S911B', deviceModelType: 2, ram: '7.63'
185
185
  },
186
186
  'samsung-s23-ultra': {
187
187
  os: 'android', platform: PLATFORM.ANDROID,
188
188
  model: 'Samsung Galaxy S23 Ultra', manufacturer: 'Samsung',
189
189
  osVersion: '14', osBuildNumber: 'UP1A.231005.007',
190
- modelId: 'SM-S918B', deviceModelType: 2
190
+ modelId: 'SM-S918B', deviceModelType: 2, ram: '11.55'
191
191
  },
192
192
  'samsung-a55': {
193
193
  os: 'android', platform: PLATFORM.ANDROID,
194
194
  model: 'Samsung Galaxy A55', manufacturer: 'Samsung',
195
195
  osVersion: '14', osBuildNumber: 'UP1A.231005.007',
196
- modelId: 'SM-A556B', deviceModelType: 1
196
+ modelId: 'SM-A556B', deviceModelType: 1, ram: '7.44'
197
197
  },
198
198
  'pixel8pro': {
199
199
  os: 'android', platform: PLATFORM.ANDROID,
200
200
  model: 'Pixel 8 Pro', manufacturer: 'Google',
201
201
  osVersion: '14', osBuildNumber: 'UP1A.231005.007',
202
- modelId: 'Pixel 8 Pro', deviceModelType: 2
202
+ modelId: 'Pixel 8 Pro', deviceModelType: 2, ram: '11.44'
203
203
  },
204
204
  'pixel8': {
205
205
  os: 'android', platform: PLATFORM.ANDROID,
206
206
  model: 'Pixel 8', manufacturer: 'Google',
207
207
  osVersion: '14', osBuildNumber: 'UP1A.231005.007',
208
- modelId: 'Pixel 8', deviceModelType: 2
208
+ modelId: 'Pixel 8', deviceModelType: 2, ram: '7.53'
209
209
  },
210
210
  'pixel7': {
211
211
  os: 'android', platform: PLATFORM.ANDROID,
212
212
  model: 'Pixel 7', manufacturer: 'Google',
213
213
  osVersion: '14', osBuildNumber: 'TP1A.221005.002',
214
- modelId: 'Pixel 7', deviceModelType: 2
214
+ modelId: 'Pixel 7', deviceModelType: 2, ram: '7.53'
215
215
  },
216
216
  'pixel7a': {
217
217
  os: 'android', platform: PLATFORM.ANDROID,
218
218
  model: 'Pixel 7a', manufacturer: 'Google',
219
219
  osVersion: '14', osBuildNumber: 'UP1A.231005.007',
220
- modelId: 'Pixel 7a', deviceModelType: 1
220
+ modelId: 'Pixel 7a', deviceModelType: 1, ram: '7.44'
221
221
  },
222
222
  'xiaomi14': {
223
223
  os: 'android', platform: PLATFORM.ANDROID,
224
224
  model: 'Xiaomi 14', manufacturer: 'Xiaomi',
225
225
  osVersion: '14', osBuildNumber: 'UP1A.231005.007',
226
- modelId: '23127PN0CG', deviceModelType: 2
226
+ modelId: '23127PN0CG', deviceModelType: 2, ram: '11.36'
227
227
  },
228
228
  'xiaomi13': {
229
229
  os: 'android', platform: PLATFORM.ANDROID,
230
230
  model: 'Xiaomi 13', manufacturer: 'Xiaomi',
231
231
  osVersion: '13', osBuildNumber: 'TQ3A.230901.001',
232
- modelId: '2211133G', deviceModelType: 2
232
+ modelId: '2211133G', deviceModelType: 2, ram: '7.51'
233
233
  },
234
234
  'oneplus12': {
235
235
  os: 'android', platform: PLATFORM.ANDROID,
236
236
  model: 'OnePlus 12', manufacturer: 'OnePlus',
237
237
  osVersion: '14', osBuildNumber: 'UP1A.231005.007',
238
- modelId: 'CPH2573', deviceModelType: 2
238
+ modelId: 'CPH2573', deviceModelType: 2, ram: '11.48'
239
239
  },
240
240
  'oneplus11': {
241
241
  os: 'android', platform: PLATFORM.ANDROID,
242
242
  model: 'OnePlus 11', manufacturer: 'OnePlus',
243
243
  osVersion: '13', osBuildNumber: 'TQ3A.230901.001',
244
- modelId: 'CPH2449', deviceModelType: 2
244
+ modelId: 'CPH2449', deviceModelType: 2, ram: '15.32'
245
245
  },
246
246
  'oppo-find-x7': {
247
247
  os: 'android', platform: PLATFORM.ANDROID,
248
248
  model: 'OPPO Find X7', manufacturer: 'OPPO',
249
249
  osVersion: '14', osBuildNumber: 'UP1A.231005.007',
250
- modelId: 'CPH2599', deviceModelType: 2
250
+ modelId: 'CPH2599', deviceModelType: 2, ram: '11.40'
251
251
  },
252
252
  'realme-gt5': {
253
253
  os: 'android', platform: PLATFORM.ANDROID,
254
254
  model: 'realme GT 5 Pro', manufacturer: 'realme',
255
255
  osVersion: '14', osBuildNumber: 'UP1A.231005.007',
256
- modelId: 'RMX3888', deviceModelType: 2
256
+ modelId: 'RMX3888', deviceModelType: 2, ram: '15.28'
257
257
  }
258
258
  };
259
259
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "whalibmob",
3
- "version": "5.29.3",
3
+ "version": "5.29.5",
4
4
  "description": "Node.js library for WhatsApp — register a number over SMS, or link as a companion by QR. Signal E2E encryption, media, groups, channels.",
5
5
  "author": "Kunboruto20",
6
6
  "main": "index.js",