Commit Graph

2344 Commits

Author SHA1 Message Date
Claude 154dd772dd feat(history): comprehensive LID-PN mapping with full JID format support
Enhances LID-PN mapping extraction to handle all WhatsApp JID formats
and extract mappings from multiple sources within history sync data.

New JID validation:
- Add `isPersonJid()` helper to identify JIDs that can have LID-PN mappings
- Skip non-person JIDs: @newsletter (channels), @broadcast, @g.us (groups)

Triple-source extraction:
1. Top-level `phoneNumberToLidMappings` array (existing)
2. Conversation objects via `lidJid`/`pnJid` properties (existing)
3. Message objects via `remoteJidAlt`/`participantAlt` fields (NEW)

New `extractLidPnFromMessage()` function:
- Extracts mappings from message key alternative JID fields
- Handles both direct messages (remoteJidAlt) and group messages (participantAlt)
- Properly identifies LID vs PN based on server type

JID formats handled:
- @s.whatsapp.net - Standard phone number
- @lid - Logical ID (privacy)
- @hosted - Hosted phone number
- @hosted.lid - Hosted LID

46 comprehensive tests covering all scenarios.

Related: WhiskeySockets/Baileys#2263
2026-01-20 22:29:36 +00:00
Claude 86c1cf439a feat(history): extract LID-PN mappings from conversation objects
WhatsApp provides LID-PN mappings in two locations within history sync:
1. Top-level `phoneNumberToLidMappings` array (already processed)
2. Individual conversation objects with `lidJid`/`pnJid` properties (new)

This change adds extraction from conversation objects, ensuring maximum
mapping coverage regardless of sync type or payload structure.

Key improvements:
- Add `extractLidPnFromConversation()` function with comprehensive JSDoc
- Use Map for O(1) deduplication of mappings across both sources
- Handle all JID formats: @lid, @hosted.lid, @s.whatsapp.net, @hosted
- Normalize JIDs using `jidNormalizedUser()` for consistency
- Skip group chats (@g.us) that don't have LID-PN mappings

Includes 22 comprehensive tests covering:
- LID chat with pnJid extraction
- PN chat with lidJid extraction
- Hosted format handling
- Deduplication between sources
- Edge cases (nulls, groups, missing data)
- All conversation sync types

Related: WhiskeySockets/Baileys#2263
See-also: WhiskeySockets/Baileys#2282
2026-01-20 22:17:09 +00:00
Renato Alcara cc4c918e1a feat(logger): add [BAILEYS] console-friendly logging functions
feat(logger): add [BAILEYS] console-friendly logging functions
2026-01-20 18:47:08 -03:00
Claude bb73662e8f fix(logger): address PR #19 code review feedback
Fixes:
- Remove unused import logBufferMetrics from event-buffer.ts
- Add safeStringify() for robust data formatting:
  - Handles circular references gracefully
  - Formats Error objects properly
  - Truncates large arrays [Array(n)]
  - Handles undefined/null/Date/BigInt values
- Add getMode() method to AdaptiveTimeoutCalculator to avoid
  duplicating mode calculation logic in flush()
- Fix empty data object handling (no trailing space)

Tests:
- Add comprehensive test suite (39 tests) covering:
  - Environment variable check (BAILEYS_LOG=false)
  - All logging functions with emoji verification
  - Session name handling
  - formatLogData edge cases (circular, Error, arrays, etc.)
2026-01-20 21:44:08 +00:00
Claude 3f2ced4501 feat(logger): add [BAILEYS] console-friendly logging functions
Add formatted logging functions with [BAILEYS] prefix and emojis:
- logEventBuffer: buffer events (📦, 🔄, ⚠️, , 🧹, 🧠)
- logBufferMetrics: metrics display (📊)
- logMessageSent/Received: message events (📤, 📥)
- logConnection: connection events (🔌, , 🔴, 🔄, )
- logAuth: authentication events (📱, 🔑, 🚪, 🔐)
- logCircuitBreaker: circuit breaker state (, , 🔶)
- logRetry: retry attempts (🔁)
- logInfo/Warn/Error: generic messages (ℹ️, ⚠️, )
- logLidMapping: LID store events (🗂️, 🔍, 💾, 📦)

All functions respect BAILEYS_LOG=false environment variable.
Integrated into event-buffer.ts and messages-send/recv.ts.
2026-01-20 20:48:46 +00:00
Renato Alcara 88b965c603 feat(logger): add comprehensive environment variable configuration
feat(logger): add comprehensive environment variable configuration
2026-01-20 17:32:36 -03:00
Renato Alcara 44fb5997a1 fix(logger): avoid pino-pretty dependency 2026-01-20 17:30:55 -03:00
Claude a462440c5c feat(logger): add comprehensive environment variable configuration
Support all logging-related environment variables:
- BAILEYS_LOG: Enable/disable logging (default: true)
- BAILEYS_LOG_LEVEL: Set log level (default: info)
- USE_STRUCTURED_LOGS: Enable structured logging (default: false)
- LOG_FORMAT: Output format - 'json' or 'pretty' (default: auto)
- LOGGER_INFO/WARN/ERROR: Enable specific log levels (default: true)

Added createFilteredLogger for level-specific filtering and
createSilentLogger for disabled logging mode.
2026-01-20 20:16:58 +00:00
Renato Alcara 68fd02b924 fix(metrics,retry): gold standard code review corrections
fix(metrics,retry): gold standard code review corrections
2026-01-20 17:06:50 -03:00
Claude 5449e3f70a fix(metrics): handle malformed URLs gracefully in metrics endpoint
Wrap URL parsing in try/catch to prevent server crashes from malformed
requests (invalid percent-encoding, problematic Host headers, etc.).
Returns 400 Bad Request instead of crashing the process.
2026-01-20 19:48:28 +00:00
Claude 6f057b8895 fix(metrics,retry): address gold standard code review
Prometheus Metrics:
- Add METRICS_LABELS fallback for defaultLabels env config
- Separate includeSystem from collectDefaultMetrics with own env var
- Parse URL in /metrics endpoint to support querystrings and trailing slashes
- Sort keys in labelsToKey for stable/deterministic lookups
- Update documentation with all environment variables

Retry Utils:
- Remove abort listener on sleep completion to prevent memory leak
- Apply maxDelay cap AFTER jitter to guarantee max delay limit
- Validate/normalize attempt parameter in calculateDelay
- Count retries only when attempt > 1 (actual retry, not first try)
- Use metrics.retryExhausted instead of generic errors for exhausted retries

Tests:
- Add consistency tests to verify retryConfigs.rsocket matches constants
2026-01-20 19:37:19 +00:00
Renato Alcara 733bede071 Merge pull request #16
fix(metrics): fix configureRegistry call signature
2026-01-20 11:49:53 -03:00
Claude 1944645556 fix(metrics): fix configureRegistry call signature
Update configureRegistry call to match new signature that accepts
only defaultLabels parameter instead of config object.
2026-01-20 14:44:53 +00:00
Renato Alcara 97b58bc011 fix(retry): resolve RETRY_BACKOFF_DELAYS initialization order error
fix(retry): resolve RETRY_BACKOFF_DELAYS initialization order error
2026-01-20 11:36:32 -03:00
Claude baf9123d0c fix(retry): address PR #15 code review feedback
- Re-export RETRY_BACKOFF_DELAYS and RETRY_JITTER_FACTOR from Defaults
  for backwards compatibility with existing imports
- Add 'as const' to RETRY_JITTER_FACTOR for type consistency
- Improve documentation explaining why values are hardcoded in retryConfigs
  (ESM initialization order issues with indirect circular imports)
2026-01-20 14:34:47 +00:00
Claude 890a80da48 fix(retry): use literal values in retryConfigs to fix ESM initialization
Hardcode values in retryConfigs.rsocket instead of referencing
RETRY_BACKOFF_DELAYS and RETRY_JITTER_FACTOR to avoid
"Cannot access before initialization" error in ESM module loading.
2026-01-20 14:25:56 +00:00
Claude cf979d6b6d fix(retry): resolve RETRY_BACKOFF_DELAYS initialization order error
- Remove duplicate RETRY_BACKOFF_DELAYS and RETRY_JITTER_FACTOR from Defaults/index.ts
- Export constants from retry-utils.ts as single source of truth
- Add 'as const' for better type inference
- Fixes "Cannot access 'RETRY_BACKOFF_DELAYS' before initialization" error
2026-01-20 14:17:18 +00:00
Renato Alcara aeec88803d Merge pull request #14
Merge pull request #14
2026-01-20 10:48:31 -03:00
Claude 37fdce4bf3 fix(metrics): address PR #14 code review feedback
- Add registryConfigured flag to ensure single execution of configureRegistry
- Fix race condition by moving setMetricPrefix/configureRegistry before Promise
- Remove unused prefix parameter from configureRegistry function
- Consolidate prefix to single source of truth (configuredPrefix global)
- Allow clearing default labels by passing empty object
- Add resetMetricsConfiguration() and getConfiguredPrefix() for testing
2026-01-20 13:45:26 +00:00
Renato Alcara 20e0efb1f7 fix(retry): address PR #12 code review feedback
fix(retry): address PR #12 code review feedback
2026-01-20 10:35:08 -03:00
Claude 6a0fefc8fe chore: resolve merge conflicts with master
Accept master version which includes:
- prom-client integration fixes from PR #11
- Retry utils improvements from PR #12
2026-01-20 13:34:14 +00:00
Claude af4563ee6a Merge remote-tracking branch 'origin/master' into claude/prom-client-nglwZ 2026-01-20 13:27:02 +00:00
Claude 82dce29dbd fix(metrics): address PR #13 code review feedback
- Apply configured prefix to all metric names via getFullMetricName()
- Configure customRegistry with defaultLabels at initialization
- Prevent memory leak: collectDefaultMetrics only called once via flag
- collectDefaultMetrics now uses customRegistry instead of global
- Initialize prefix/defaultLabels before creating baileysMetrics

All metrics now properly include prefix (e.g., baileys_connection_attempts)
and inherit defaultLabels configured via environment variables.
2026-01-20 13:25:21 +00:00
Renato Alcara 168de69e73 fix(metrics): address PR #11 code review feedback
fix(metrics): address PR #11 code review feedback
2026-01-20 10:20:18 -03:00
Claude 4924912f85 fix(metrics): address PR #11 code review feedback
Major improvements to prometheus-metrics.ts:
- Use custom registry instead of global promClient.register (isolation)
- Remove duplicate localValues - prom-client is now single source of truth
- Fix reset(labels) to respect labels param using remove() instead of reset()
- Migrate Summary class to use prom-client internally
- getMetricsOutput() now uses customRegistry for proper isolation

Fix misleading comments in retry-utils.ts:
- Change "exponential backoff" to "custom progressive backoff"
- Fix comment claiming constants are "from Defaults" (now local)

Breaking changes to getValues()/get() - now async as they query prom-client
2026-01-20 13:16:43 +00:00
Renato Alcara 833d6b14af b719349 fix(retry): address PR #12 code review feedback
b719349 fix(retry): address PR #12 code review feedback
2026-01-20 10:12:03 -03:00
Claude b719349c57 fix(retry): address PR #12 code review feedback
- Add 'stepped' backoff strategy that uses RETRY_BACKOFF_DELAYS directly
- Update rsocket config to use 'stepped' instead of 'exponential'
- Clarify maxWebSocketListeners calculation (8 core + 10 dynamic + 2 buffer)
- Document maxSocketClientListeners calculation (20 core + 20 dynamic + 10 buffer)
- Change 'exponential backoff' to 'custom progressive backoff' in docs
- Add comprehensive tests for getRetryDelayWithJitter and getAllRetryDelaysWithJitter
- Fix existing test type errors (onRetry mock, always/never predicates)
2026-01-20 13:05:13 +00:00
Renato Alcara b21847addb Merge branch 'WhiskeySockets:master' into master 2026-01-20 09:58:02 -03:00
Claude 2d84da8bd7 fix(retry): resolve circular dependency with Defaults module
Define RETRY_BACKOFF_DELAYS and RETRY_JITTER_FACTOR locally in
retry-utils.ts to avoid circular dependency that caused
"Cannot access 'RETRY_BACKOFF_DELAYS' before initialization" error.
2026-01-20 12:37:18 +00:00
Claude 43ece09fe9 feat(metrics): integrate prom-client for native Prometheus support
- Add prom-client ^15.1.3 as production dependency
- Migrate Counter class to use prom-client internally
- Migrate Gauge class to use prom-client internally
- Migrate Histogram class to use prom-client internally
- Update getMetricsOutput() to use prom-client's native metrics()
- Update contentType() to use prom-client's contentType
- Enable collectDefaultMetrics() for Node.js system metrics
- Maintain backward compatibility with existing API

Benefits:
- Native OpenMetrics format export
- Proper histogram bucket handling
- Default Node.js metrics (memory, CPU, event loop, GC)
- Better integration with Grafana/Prometheus ecosystem
2026-01-20 12:37:17 +00:00
Claude e605a02528 fix(defaults): address PR #10 code review feedback
- Integrate RETRY_BACKOFF_DELAYS and RETRY_JITTER_FACTOR into retry-utils.ts
  - Add retryConfigs.rsocket using the default delays
  - Add getRetryDelayWithJitter() helper function
  - Add getAllRetryDelaysWithJitter() for planning
- Document DEFAULT_CACHE_MAX_KEYS with usage example
- Adjust INITIAL_PREKEY_COUNT from 30 to 200 (moderate value)
- Adjust MIN_UPLOAD_INTERVAL from 60s to 10s (balance rate limiting/responsiveness)
- Revert syncFullHistory to true (avoid breaking change)
2026-01-20 12:36:52 +00:00
Claude 6f75e5ac21 feat(socket): add configurable maxListeners to prevent memory leaks
Based on RSocket's battle-tested configuration:

- Add maxWebSocketListeners config option (default: 20)
  - 8 base WS events + 10 dynamic listeners + 2 buffer slots
- Add maxSocketClientListeners config option (default: 50)
- Replace dangerous setMaxListeners(0) with configurable limits
- Add warning log if user explicitly sets limit to 0

BREAKING: Previous behavior used setMaxListeners(0) which removed
all limits. Now defaults to safe limits but can be overridden via config.
2026-01-20 12:36:51 +00:00
Claude 682b62acbf feat(defaults): apply RSocket's battle-tested configurations
- Add DEFAULT_CACHE_MAX_KEYS with limits per store type (prevents memory leaks)
- Add RETRY_BACKOFF_DELAYS [1s, 2s, 5s, 10s, 20s] for exponential backoff
- Add RETRY_JITTER_FACTOR (0.15) to prevent thundering herd
- Change INITIAL_PREKEY_COUNT from 812 to 30 (safer for rate limiting)
- Change MIN_UPLOAD_INTERVAL from 5s to 60s (avoids rate limiting)
- Change syncFullHistory default to false (conservative approach)

Based on RSocket fork's production-tested configuration.
2026-01-20 12:36:51 +00:00
Claude 7f9970fa06 fix(retry): resolve circular dependency with Defaults module
Define RETRY_BACKOFF_DELAYS and RETRY_JITTER_FACTOR locally in
retry-utils.ts to avoid circular dependency that caused
"Cannot access 'RETRY_BACKOFF_DELAYS' before initialization" error.
2026-01-20 12:31:34 +00:00
Claude 673bf6e69f feat(metrics): integrate prom-client for native Prometheus support
- Add prom-client ^15.1.3 as production dependency
- Migrate Counter class to use prom-client internally
- Migrate Gauge class to use prom-client internally
- Migrate Histogram class to use prom-client internally
- Update getMetricsOutput() to use prom-client's native metrics()
- Update contentType() to use prom-client's contentType
- Enable collectDefaultMetrics() for Node.js system metrics
- Maintain backward compatibility with existing API

Benefits:
- Native OpenMetrics format export
- Proper histogram bucket handling
- Default Node.js metrics (memory, CPU, event loop, GC)
- Better integration with Grafana/Prometheus ecosystem
2026-01-20 12:01:10 +00:00
Renato Alcara 1e534bb7a8 feat(defaults): apply RSocket battle-tested configurations for stability
feat(defaults): apply RSocket battle-tested configurations for stability
2026-01-20 08:44:14 -03:00
Rajeh Taher b6b708ddfe chore(tests): lint 2026-01-20 12:47:05 +02:00
Enzo Nascimento a1d69f72c9 fix(utils.normalizeMessageContent): add associatedChildMessage as one of the options to normalize (#1874)
Co-authored-by: Rajeh Taher <rajeh@reforward.dev>
2026-01-20 12:46:03 +02:00
Rajeh Taher 90e8ba82f4 Cache the children after a getBinaryNodeChild/ren call to avoid traversing arrays (#2093)
* generic-utils: cache the get

* generic-utils: increased type safety

* chore: lint
2026-01-20 12:43:27 +02:00
David ??? d36d9c194c Add groupStatusMessage checks in message handling (#2258) 2026-01-20 12:41:33 +02:00
João Lucas de Oliveira Lopes 8ff01b8bb3 fix: store LID-PN mapping from contactAction sync (#2266)
* fix: store LID-PN mapping from contactAction sync

* chore: improve testing of sync actions
2026-01-20 12:39:41 +02:00
João Lucas de Oliveira Lopes a89736f89d fix: extract LID-PN mappings from history sync phoneNumberToLidMappings (#2268) 2026-01-20 12:39:29 +02:00
Luiz Braga 32134a870e chore: Add messageTimestamp to message updates in messages-recv when receiving a message status update (#2277) 2026-01-20 12:37:34 +02:00
João Lucas de Oliveira Lopes 5887551d68 fix: resolve race condition in decodeFrame handling and improve encryption integrity (#2182)
* fix: resolve race condition in decodeFrame handling and improve encryption integrity

* chore: pr feedback
2026-01-20 12:37:04 +02:00
github-actions[bot] 4bdcedf96b chore: update WhatsApp Web version (#2269)
Co-authored-by: github-actions[bot] <github-actions[bot]@users.noreply.github.com>
2026-01-20 12:35:35 +02:00
Claude 4a2731fbbd fix(defaults): address PR #10 code review feedback
- Integrate RETRY_BACKOFF_DELAYS and RETRY_JITTER_FACTOR into retry-utils.ts
  - Add retryConfigs.rsocket using the default delays
  - Add getRetryDelayWithJitter() helper function
  - Add getAllRetryDelaysWithJitter() for planning
- Document DEFAULT_CACHE_MAX_KEYS with usage example
- Adjust INITIAL_PREKEY_COUNT from 30 to 200 (moderate value)
- Adjust MIN_UPLOAD_INTERVAL from 60s to 10s (balance rate limiting/responsiveness)
- Revert syncFullHistory to true (avoid breaking change)
2026-01-20 05:33:03 +00:00
Claude 3afb8b80c5 feat(socket): add configurable maxListeners to prevent memory leaks
Based on RSocket's battle-tested configuration:

- Add maxWebSocketListeners config option (default: 20)
  - 8 base WS events + 10 dynamic listeners + 2 buffer slots
- Add maxSocketClientListeners config option (default: 50)
- Replace dangerous setMaxListeners(0) with configurable limits
- Add warning log if user explicitly sets limit to 0

BREAKING: Previous behavior used setMaxListeners(0) which removed
all limits. Now defaults to safe limits but can be overridden via config.
2026-01-20 05:19:22 +00:00
Claude 4f623b4942 feat(defaults): apply RSocket's battle-tested configurations
- Add DEFAULT_CACHE_MAX_KEYS with limits per store type (prevents memory leaks)
- Add RETRY_BACKOFF_DELAYS [1s, 2s, 5s, 10s, 20s] for exponential backoff
- Add RETRY_JITTER_FACTOR (0.15) to prevent thundering herd
- Change INITIAL_PREKEY_COUNT from 812 to 30 (safer for rate limiting)
- Change MIN_UPLOAD_INTERVAL from 5s to 60s (avoids rate limiting)
- Change syncFullHistory default to false (conservative approach)

Based on RSocket fork's production-tested configuration.
2026-01-20 05:12:05 +00:00
Renato Alcara aa2ff855bd feat(lid-mapping): enhance with enterprise-grade features
feat(lid-mapping): enhance with enterprise-grade features
2026-01-20 02:06:23 -03:00
Claude 4e68f9885c fix(lid-mapping): address PR #9 code review feedback
- Add bounds validation for config values (prevent DoS via env vars)
- Replace ?? false with || false in isValidMapping (correct operator)
- Rename deleteMapping to deleteMappingFromCache (clarify behavior)
- Keep deleteMapping as deprecated alias for backward compatibility
- Document destroyed state handling in read-only methods
- Document async metrics module loading race condition
- Document storeLIDPNMappings return type change
- Add failure tracking and warning in getLIDsForPNs
- Document exponential backoff retry pattern in config and method
2026-01-20 05:04:25 +00:00