qwen_2.5_model / src /engine /engine-capability-matrix.ts
Muhammad Noman
Deploy OpenWA to Hugging Face Spaces
46252cd
Raw
History Blame Contribute Delete
17 kB
/**
* Committed engine capability matrix: for each `IWhatsAppEngine` method, the REAL availability on
* each adapter β€” `wwjs` = whatsapp-web.js (the default engine), `baileys` = the browser-free
* alternative.
*
* Two fields tell the story:
* - `status`: 'supported' (the capability genuinely works end-to-end) or 'not-available' (the method
* either throws `EngineNotSupportedError`/`ChannelMediaNotSupportedError` at the adapter boundary
* β†’ HTTP 501, OR the adapter claims support but the underlying library cannot deliver β€” a
* phantom-support case surfaced by source verification, e.g. wwjs catalog methods that log
* "not implemented" and return null/[] without throwing).
* - `rootCause` (present only when `not-available`): WHY it is not available, so a contributor knows
* exactly where to start. Three values:
* 'adapter-gap' β€” the underlying library HAS the capability; only the OpenWA adapter
* wiring is missing. FIXABLE in this repo (a PR that calls the library
* symbol the evidence points at).
* 'library-limitation' β€” the underlying library exposes NO first-class symbol for this op. Not
* fixable without a raw-proto/fork effort or an event-cache hack.
* 'uncertain' β€” source trace was inconclusive; needs a live spike.
*
* `evidence` cites the library symbol(s) that were inspected, so an engineer can open the exact file
* and start wiring immediately. REQUIRED when at least one adapter is `not-available`; may also
* annotate a newly-wired `supported` row with the symbols it now calls.
*
* This is a SNAPSHOT. `engine-parity.spec.ts` enforces exact matrix-key↔interface-method correspondence
* and the throw-invariants it can observe in live adapter method bodies. It does not read the operator
* documentation and cannot classify non-throwing phantom stubs. The `status`, `rootCause`, and
* `evidence` fields therefore remain hand-curated, source-traced annotations that must be reviewed as
* adapters are wired or libraries change.
*
* NOTE on phantom support: the drift gate's throw-heuristic cannot see adapter methods that silently
* stub (return null/[] + a warn log) without throwing. The matrix BELOW is the source-of-truth: three
* wwjs entries (getCatalog/getProducts/getProduct) are marked `not-available` here even though their
* adapter bodies do not throw β€” the library has no API for them, so the adapter stubs. If the drift
* gate is extended to assert against this matrix, it must consult `status`, not just the throw
* pattern, for these rows (or the adapter stubs must start throwing). getContactStatus/
* getContactStatuses were on this list until #714 wired them on whatsapp-web.js; their rows say
* `supported` and the adapter really does read stories, so they no longer belong here.
*/
export type CapabilityStatus = 'supported' | 'not-available';
export type RootCause = 'adapter-gap' | 'library-limitation' | 'uncertain';
export interface AdapterCapability {
status: CapabilityStatus;
/** Present only when `status === 'not-available'`. */
rootCause?: RootCause;
}
export interface MethodCapability {
wwjs: AdapterCapability;
baileys: AdapterCapability;
/** Cited library symbols (baileys; wwjs). Required when at least one adapter is not-available. */
evidence?: string;
}
export const ENGINE_CAPABILITY_MATRIX: Record<string, MethodCapability> = {
addLabelToChat: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
addParticipants: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
blockContact: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
checkNumberExists: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
createGroup: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
deleteChat: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
deleteMessage: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
deleteStatus: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
demoteParticipants: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
destroy: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
disconnect: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
editMessage: {
wwjs: { status: 'supported' },
baileys: { status: 'supported' },
evidence:
'wwjs Message.edit(content,options?) (index.d.ts:1362; MessageEditOptions:1600); baileys Editable.edit?: WAMessageKey on the text content variant (Types/Message.d.ts:86, AnyRegularMessageContent:168) via sendMessage(jid,{text,edit:key})',
},
forceDestroy: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
forwardMessage: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
getCatalog: {
wwjs: { status: 'not-available', rootCause: 'library-limitation' },
baileys: { status: 'not-available', rootCause: 'adapter-gap' },
evidence:
'baileys Socket/business.d.ts:7 getCatalog({jid,limit,cursor}) + getCollections (business.d.ts:11) β€” adapter unwired (returns Product[]+cursor, not Catalog metadata; medium-confidence shape synthesis); wwjs index.d.ts has NO Client.getCatalog (0 hits), adapter stubs to null @WhatsAppWebJsAdapter.getCatalog',
},
getChannelById: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
getChannelMessages: {
wwjs: { status: 'supported' },
baileys: { status: 'not-available', rootCause: 'adapter-gap' },
evidence:
'baileys Socket/newsletter.d.ts:19 newsletterFetchMessages(jid,count,since,after) returns RAW BinaryNode of <message_updates> (newsletter.js:149) — adapter unwired AND no exposed library parser (BinaryNode→ChannelMessage mapping is the work); wwjs Channel.fetchMessages (Channel.js:327)',
},
getChatHistory: {
wwjs: { status: 'supported' },
baileys: { status: 'not-available', rootCause: 'library-limitation' },
evidence:
'baileys only fetchMessageHistory(count,oldestKey,oldestTs) (Socket/business.d.ts:25) returns a sync-token string; messages arrive later via messaging-history.set event β€” no synchronous per-chat fetchMessages; wwjs Chat.fetchMessages (Chat.js)',
},
getChatLabels: {
wwjs: { status: 'supported' },
baileys: { status: 'not-available', rootCause: 'library-limitation' },
evidence:
'baileys no getChatLabels in lib/**/*.d.ts; Types/LabelAssociation.d.ts defines ChatLabelAssociation but no query fn (only addChatLabel/removeChatLabel writes @chats.d.ts:70-71); wwjs Client.getChatLabels (Client.js:2838)',
},
getChats: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
getContactById: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
getContactStatus: {
wwjs: { status: 'supported' },
baileys: { status: 'not-available', rootCause: 'library-limitation' },
evidence:
'baileys fetchStatus (Socket/chats.d.ts:42 via USyncStatusProtocol) = about/profile text only, NOT 24h stories β€” no story getter in lib',
},
getContactStatuses: {
wwjs: { status: 'supported' },
baileys: { status: 'not-available', rootCause: 'library-limitation' },
evidence: 'baileys fetchStatus = about text only; no story enumerate in lib',
},
getContacts: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
getGroupInfo: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
getGroupInviteCode: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
getGroups: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
getLabelById: {
wwjs: { status: 'supported' },
baileys: { status: 'not-available', rootCause: 'library-limitation' },
evidence:
'baileys no getLabel/getLabelById in lib/**/*.d.ts (Types/Label.d.ts has only Label interface + LabelColor enum + LabelActionBody); derivable only from an app-state-sync label cache; wwjs Client.getLabelById (Client.js:2825)',
},
getLabels: {
wwjs: { status: 'supported' },
baileys: { status: 'not-available', rootCause: 'library-limitation' },
evidence:
'baileys no getLabel/fetchLabel in lib/**/*.d.ts; chats.d.ts:69-73 + business.d.ts:162-166 expose ONLY writes; derivable only from an app-state-sync event cache; wwjs Client.getLabels (Client.js:2747)',
},
getMessageReactions: {
wwjs: { status: 'supported' },
baileys: { status: 'not-available', rootCause: 'library-limitation' },
evidence:
'baileys no getReactions/fetchReactions; reactions exist only as event-augmented WAMessage.reactions (proto.IReaction @WAProto/index.d.ts:10623) via messages.reaction event; adapter does not persist them into its store; wwjs Message.getReactions (Message.js)',
},
getNumberId: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
getPhoneNumber: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
getProduct: {
wwjs: { status: 'not-available', rootCause: 'library-limitation' },
baileys: { status: 'not-available', rootCause: 'adapter-gap' },
evidence:
'baileys only getCatalog (Socket/business.d.ts:7); getProduct = getCatalog then find-by-id (compose-and-filter, loads whole page; medium-confidence); wwjs no Client.getProduct β€” only page-internal getProductMetadata (Utils.js:1253), not a public Client fn; adapter stubs to null @WhatsAppWebJsAdapter.getProduct',
},
getProducts: {
wwjs: { status: 'not-available', rootCause: 'library-limitation' },
baileys: { status: 'not-available', rootCause: 'adapter-gap' },
evidence:
'baileys Socket/business.d.ts:7 getCatalog({jid,limit,cursor}) β†’ {products, nextPageCursor} β€” adapter unwired; wwjs no Client.getProducts in index.d.ts (0 hits); adapter stubs to empty @WhatsAppWebJsAdapter.getProducts',
},
getProfilePicture: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
getPushName: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
getQRCode: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
getStatus: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
getSubscribedChannels: {
wwjs: { status: 'supported' },
baileys: { status: 'not-available', rootCause: 'library-limitation' },
evidence:
'baileys no enumerate-newsletters fn; all 23 Socket/newsletter.d.ts exports are per-jid (newsletterMetadata requires a key; newsletterSubscribers returns the count of ONE). Only the newsletter EVENT surfaces jids opportunistically (incremental, not list-all); wwjs Client.getChannels (Client.js:1680)',
},
initialize: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
joinGroupViaInviteCode: {
wwjs: { status: 'supported' },
baileys: { status: 'supported' },
evidence:
'wwjs Client.acceptInvite(inviteCode) β†’ res.gid._serialized (index.d.ts:23; Client.js:1836-1844); baileys groupAcceptInvite(code) β†’ string|undefined (Socket/groups.d.ts:25) β€” undefined mapped to a thrown error',
},
leaveGroup: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
logout: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
markUnread: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
postImageStatus: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
postTextStatus: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
postVideoStatus: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
promoteParticipants: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
reactToMessage: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
removeLabelFromChat: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
removeParticipants: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
rejectCall: {
wwjs: { status: 'supported' },
baileys: { status: 'supported' },
evidence:
"wwjs Call.reject() (index.d.ts:2417) on the live Call cached from the client 'call' event (index.d.ts:643); baileys rejectCall(callId, callFrom) (Socket/messages-recv.d.ts:10) with the raw `from` JID cached from the 'offer' call event (Types/Call.d.ts)",
},
replyToMessage: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
requestPairingCode: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
resolveContactPhone: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
revokeGroupInviteCode: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
sendAudioMessage: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
sendCatalog: {
wwjs: { status: 'not-available', rootCause: 'library-limitation' },
baileys: { status: 'not-available', rootCause: 'library-limitation' },
evidence:
'baileys AnyMessageContent (Types/Message.d.ts:166-210) has no catalog key β€” only {product} single-product + product_catalog_edit/add/delete CRUD (Socket/business.js:294-362); wwjs no Client.sendCatalog in index.d.ts (0 hits)',
},
sendChatState: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
sendContactMessage: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
sendDocumentMessage: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
sendImageMessage: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
sendLocationMessage: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
sendPollMessage: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
sendProduct: {
wwjs: { status: 'not-available', rootCause: 'library-limitation' },
baileys: { status: 'not-available', rootCause: 'adapter-gap' },
evidence:
'baileys AnyRegularMessageContent {product: WASendableProduct} (Types/Message.d.ts:203) built in messages.js:397 β€” adapter unwired (2-step: getCatalog lookup for image/title/price THEN sendMessage); wwjs no Client.sendProduct β€” Product/Order are inbound-only parsers',
},
sendSeen: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
sendStickerMessage: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
sendTextMessage: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
sendVideoMessage: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
setGroupDescription: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
setGroupEphemeral: {
wwjs: { status: 'not-available', rootCause: 'library-limitation' },
baileys: { status: 'supported' },
evidence:
'wwjs 1.34.7 exposes NO ephemeral setter β€” 0 hits for ephemeral in index.d.ts; only a create-time messageTimer option (Client.js:2371); adapter throws EngineNotSupportedError; baileys groupToggleEphemeral(jid, ephemeralExpiration) (Socket/groups.d.ts:40)',
},
setGroupInfoAdminsOnly: {
wwjs: { status: 'supported' },
baileys: { status: 'supported' },
evidence:
"wwjs GroupChat.setInfoAdminsOnly(adminsOnly?) (index.d.ts:2216; sets groupMetadata.restrict, GroupChat.js:544); baileys groupSettingUpdate(jid, 'locked'|'unlocked') (Socket/groups.d.ts:41)",
},
setGroupMessagesAdminsOnly: {
wwjs: { status: 'supported' },
baileys: { status: 'supported' },
evidence:
"wwjs GroupChat.setMessagesAdminsOnly(adminsOnly?) (index.d.ts:2210; sets groupMetadata.announce, GroupChat.js:513); baileys groupSettingUpdate(jid, 'announcement'|'not_announcement') (Socket/groups.d.ts:41)",
},
setGroupSubject: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
setProfileName: {
wwjs: { status: 'supported' },
baileys: { status: 'supported' },
evidence:
'wwjs Client.setDisplayName(displayName) β†’ boolean (index.d.ts:251; false β†’ adapter throws); baileys updateProfileName(name) (Socket/chats.d.ts:50)',
},
setProfilePicture: {
wwjs: { status: 'supported' },
baileys: { status: 'supported' },
evidence:
'wwjs Client.setProfilePicture(MessageMedia) β†’ boolean (index.d.ts:336; false β†’ adapter throws); baileys updateProfilePicture(ownJid, WAMediaUpload) (Socket/chats.d.ts:44)',
},
setProfileStatus: {
wwjs: { status: 'supported' },
baileys: { status: 'supported' },
evidence:
'wwjs Client.setStatus(status) (index.d.ts:245); baileys updateProfileStatus(status) (Socket/chats.d.ts:49)',
},
subscribeToChannel: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
unblockContact: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
unsubscribeFromChannel: { wwjs: { status: 'supported' }, baileys: { status: 'supported' } },
};