Summary
The @lid → phone resolution added in #263 (RESOLVE_LID_TO_PHONE, senderPhone on message.received, and GET /sessions/:id/contacts/:contactId/phone) works on the whatsapp-web.js adapter but is effectively non-functional on the Baileys engine: senderPhone and the on-demand endpoint return null even for known/saved contacts.
Environment
- OpenWA v0.4.3 (current
main)
- Engine: Baileys
RESOLVE_LID_TO_PHONE=true
Symptoms
Inbound message from an @lid sender the account has interacted with before (the same contact previously appeared by phone number, before WhatsApp's LID migration):
message.received payload: isLidSender: true but senderPhone: null
GET /api/sessions/:sid/contacts/<id>@lid/phone → { "contactId": "<id>@lid", "phone": null }
So isLidSender (engine-neutral detection) works, but the resolution (adapter-specific) never returns a number on Baileys — even after the contact sends a fresh message.
Root cause
The Baileys resolution only consults two in-memory maps and has no server-query / lidMapping fallback, unlike the wwebjs adapter which uses getContactLidAndPhone() (the server-query fallback that was the whole point in #263).
src/engine/adapters/baileys.adapter.ts:
async resolveContactPhone(contactId: string): Promise<string | null> {
this.ensureReady();
return this.sessionStore.resolvePhone(contactId);
}
src/engine/adapters/baileys-session-store.ts:
resolvePhone(id: string): string | null {
if (id.endsWith('@s.whatsapp.net')) return this.userPart(id);
if (id.endsWith('@lid')) {
const pn = this.lidToPn.get(id);
if (pn) return this.userPart(pn);
const contactPhone = this.contacts.get(id)?.phoneNumber;
return contactPhone ? this.userPart(contactPhone) : null; // null when not pre-cached
}
return null;
}
If the lid → pn mapping isn't already in lidToPn / contacts, it returns null with no attempt to resolve. In practice those maps aren't populated for an inbound @lid sender (a fresh inbound message still yields null), so the feature never fires on Baileys.
Contrast — src/engine/adapters/whatsapp-web-js.adapter.ts uses client.getContactLidAndPhone([id]), which does a server-side query and resolves contacts even when not locally cached.
Suggested fix
Give the Baileys resolvePhone a real fallback, e.g.:
- Populate
lidToPn from inbound message metadata — Baileys exposes the PN alongside the LID (message key senderPn / participantPn, and the lid-mapping.update event / messages.upsert lid info).
- Query Baileys' LID mapping store as a fallback:
sock.signalRepository.lidMapping.getPNForLID(lid) (and/or a USync / onWhatsApp lookup), mirroring the server-query fallback the wwebjs adapter gets from getContactLidAndPhone.
Happy to test a patch on a live Baileys session.
Repro
- Baileys session,
RESOLVE_LID_TO_PHONE=true.
- Receive a message from a contact WhatsApp now addresses as
@lid (one you've messaged before).
- Observe
senderPhone: null on the payload and null from GET .../contacts/<lid>/phone.
Related: #263.
Summary
The
@lid→ phone resolution added in #263 (RESOLVE_LID_TO_PHONE,senderPhoneonmessage.received, andGET /sessions/:id/contacts/:contactId/phone) works on the whatsapp-web.js adapter but is effectively non-functional on the Baileys engine:senderPhoneand the on-demand endpoint returnnulleven for known/saved contacts.Environment
main)RESOLVE_LID_TO_PHONE=trueSymptoms
Inbound message from an
@lidsender the account has interacted with before (the same contact previously appeared by phone number, before WhatsApp's LID migration):message.receivedpayload:isLidSender: truebutsenderPhone: nullGET /api/sessions/:sid/contacts/<id>@lid/phone→{ "contactId": "<id>@lid", "phone": null }So
isLidSender(engine-neutral detection) works, but the resolution (adapter-specific) never returns a number on Baileys — even after the contact sends a fresh message.Root cause
The Baileys resolution only consults two in-memory maps and has no server-query / lidMapping fallback, unlike the wwebjs adapter which uses
getContactLidAndPhone()(the server-query fallback that was the whole point in #263).src/engine/adapters/baileys.adapter.ts:src/engine/adapters/baileys-session-store.ts:If the
lid → pnmapping isn't already inlidToPn/contacts, it returnsnullwith no attempt to resolve. In practice those maps aren't populated for an inbound@lidsender (a fresh inbound message still yieldsnull), so the feature never fires on Baileys.Contrast —
src/engine/adapters/whatsapp-web-js.adapter.tsusesclient.getContactLidAndPhone([id]), which does a server-side query and resolves contacts even when not locally cached.Suggested fix
Give the Baileys
resolvePhonea real fallback, e.g.:lidToPnfrom inbound message metadata — Baileys exposes the PN alongside the LID (message keysenderPn/participantPn, and thelid-mapping.updateevent /messages.upsertlid info).sock.signalRepository.lidMapping.getPNForLID(lid)(and/or a USync /onWhatsApplookup), mirroring the server-query fallback the wwebjs adapter gets fromgetContactLidAndPhone.Happy to test a patch on a live Baileys session.
Repro
RESOLVE_LID_TO_PHONE=true.@lid(one you've messaged before).senderPhone: nullon the payload andnullfromGET .../contacts/<lid>/phone.Related: #263.