Skip to content

Instantly share code, notes, and snippets.

@PurpShell
Last active June 30, 2024 09:02
Show Gist options
  • Save PurpShell/9e9200632abfd6289b89cca1f9ebd1ba to your computer and use it in GitHub Desktop.
Save PurpShell/9e9200632abfd6289b89cca1f9ebd1ba to your computer and use it in GitHub Desktop.
A script to monitor messages in a WhatsApp socket - If you find this useful, please donate ( https://github.com/sponsors/Purpshell ) :D
// some code to inject into whatsapp web, handles socket message decryption and logging and also provides Store.
// Copyright PurpShell/Rajeh Taher ~ 2023
// also, check out my GitHub Sponsors @purpshell if you find this useful to you!
if (!window.mR) {
const moduleRaid = function () {
moduleRaid.mID = Math.random().toString(36).substring(7);
moduleRaid.mObj = {};
fillModuleArray = function () {
(window.webpackChunkbuild || window.webpackChunkwhatsapp_web_client).push([
[moduleRaid.mID], {}, function (e) {
Object.keys(e.m).forEach(function (mod) {
moduleRaid.mObj[mod] = e(mod);
})
}
]);
}
fillModuleArray();
get = function get(id) {
return moduleRaid.mObj[id]
}
findModule = function findModule(query) {
results = [];
modules = Object.keys(moduleRaid.mObj);
modules.forEach(function (mKey) {
mod = moduleRaid.mObj[mKey];
if (typeof mod !== 'undefined') {
if (typeof query === 'string') {
if (typeof mod.default === 'object') {
for (key in mod.default) {
if (key == query) results.push(mod);
}
}
for (key in mod) {
if (key == query) results.push(mod);
}
} else if (typeof query === 'function') {
if (query(mod)) {
results.push(mod);
}
} else {
throw new TypeError('findModule can only find via string and function, ' + (typeof query) + ' was passed');
}
}
})
return results;
}
return {
modules: moduleRaid.mObj,
constructors: moduleRaid.cArr,
findModule: findModule,
get: get
}
}
window.mR = moduleRaid();
}
if (!window.Store) {
window.Store = Object.assign({}, window.mR.findModule(m => m.default && m.default.Chat)[0].default);
window.Store.AppState = window.mR.findModule('Socket')[0].Socket;
window.Store.Conn = window.mR.findModule('Conn')[0].Conn;
window.Store.BlockContact = window.mR.findModule('blockContact')[0];
window.Store.Call = window.mR.findModule((module) => module.default && module.default.Call)[0].default.Call;
window.Store.Cmd = window.mR.findModule('Cmd')[0].Cmd;
window.Store.CryptoLib = window.mR.findModule('decryptE2EMedia')[0];
window.Store.DownloadManager = window.mR.findModule('downloadManager')[0].downloadManager;
window.Store.GroupMetadata = window.mR.findModule('GroupMetadata')[0].default.GroupMetadata;
window.Store.Invite = window.mR.findModule('resetGroupInviteCode')[0];
window.Store.InviteInfo = window.mR.findModule('queryGroupInvite')[0];
window.Store.Label = window.mR.findModule('LabelCollection')[0].LabelCollection;
window.Store.MediaPrep = window.mR.findModule('prepRawMedia')[0];
window.Store.MediaObject = window.mR.findModule('getOrCreateMediaObject')[0];
window.Store.NumberInfo = window.mR.findModule('formattedPhoneNumber')[0];
window.Store.MediaTypes = window.mR.findModule('msgToMediaType')[0];
window.Store.MediaUpload = window.mR.findModule('uploadMedia')[0];
window.Store.MsgKey = window.mR.findModule((module) => module.default && module.default.fromString)[0].default;
window.Store.MessageInfo = window.mR.findModule('sendQueryMsgInfo')[0];
window.Store.OpaqueData = window.mR.findModule(module => module.default && module.default.createFromData)[0].default;
window.Store.QueryExist = window.mR.findModule('queryExists')[0] ? window.mR.findModule('queryExists')[0].queryExists : window.mR.findModule('queryExist')[0].queryWidExists;
window.Store.QueryProduct = window.mR.findModule('queryProduct')[0];
window.Store.QueryOrder = window.mR.findModule('queryOrder')[0];
window.Store.SendClear = window.mR.findModule('sendClear')[0];
window.Store.SendDelete = window.mR.findModule('sendDelete')[0];
window.Store.SendMessage = window.mR.findModule('addAndSendMsgToChat')[0];
window.Store.EditMessage = window.mR.findModule('addAndSendMessageEdit')[0];
window.Store.SendSeen = window.mR.findModule('sendSeen')[0];
window.Store.User = window.mR.findModule('getMaybeMeUser')[0];
window.Store.ContactMethods = window.mR.findModule('getUserid')[0];
window.Store.BusinessProfileCollection = window.mR.findModule('BusinessProfileCollection')[0].BusinessProfileCollection;
window.Store.UploadUtils = window.mR.findModule((module) => (module.default && module.default.encryptAndUpload) ? module.default : null)[0].default;
window.Store.UserConstructor = window.mR.findModule((module) => (module.default && module.default.prototype && module.default.prototype.isServer && module.default.prototype.isUser) ? module.default : null)[0].default;
window.Store.Validators = window.mR.findModule('findLinks')[0];
window.Store.VCard = window.mR.findModule('vcardFromContactModel')[0];
window.Store.WidFactory = window.mR.findModule('createWid')[0];
window.Store.ProfilePic = window.mR.findModule('profilePicResync')[0];
window.Store.PresenceUtils = window.mR.findModule('sendPresenceAvailable')[0];
window.Store.ChatState = window.mR.findModule('sendChatStateComposing')[0];
window.Store.GroupParticipants = window.mR.findModule('promoteParticipants')[0];
window.Store.JoinInviteV4 = window.mR.findModule('queryGroupInviteV4')[0];
window.Store.findCommonGroups = window.mR.findModule('findCommonGroups')[0].findCommonGroups;
window.Store.StatusUtils = window.mR.findModule('setMyStatus')[0];
window.Store.ConversationMsgs = window.mR.findModule('loadEarlierMsgs')[0];
window.Store.sendReactionToMsg = window.mR.findModule('sendReactionToMsg')[0].sendReactionToMsg;
window.Store.createOrUpdateReactionsModule = window.mR.findModule('createOrUpdateReactions')[0];
window.Store.EphemeralFields = window.mR.findModule('getEphemeralFields')[0];
window.Store.ReplyUtils = window.mR.findModule('canReplyMsg').length > 0 && window.mR.findModule('canReplyMsg')[0];
window.Store.MsgActionChecks = window.mR.findModule('canSenderRevokeMsg')[0];
window.Store.QuotedMsg = window.mR.findModule('getQuotedMsgObj')[0];
window.Store.Socket = window.mR.findModule('deprecatedSendIq')[0];
window.Store.SocketWap = window.mR.findModule('wap')[0];
window.Store.SearchContext = window.mR.findModule('getSearchContext')[0].getSearchContext;
window.Store.DrawerManager = window.mR.findModule('DrawerManager')[0].DrawerManager;
window.Store.StickerTools = {
...window.mR.findModule('toWebpSticker')[0],
...window.mR.findModule('addWebpMetadata')[0]
};
window.Store.GroupUtils = {
...window.mR.findModule('createGroup')[0],
...window.mR.findModule('setGroupDescription')[0],
...window.mR.findModule('sendExitGroup')[0],
...window.mR.findModule('sendSetPicture')[0]
};
if (!window.Store.Chat._find) {
window.Store.Chat._find = e => {
const target = window.Store.Chat.get(e);
return target ? Promise.resolve(target) : Promise.resolve({
id: e
});
};
}
if (window.mR.findModule('ChatCollection')[0] && window.mR.findModule('ChatCollection')[0].ChatCollection) {
if (typeof window.mR.findModule('ChatCollection')[0].ChatCollection.findImpl === 'undefined' && typeof window.mR.findModule('ChatCollection')[0].ChatCollection._find != 'undefined') {
window.mR.findModule('ChatCollection')[0].ChatCollection.findImpl = window.mR.findModule('ChatCollection')[0].ChatCollection._find;
}
}
/**
* Helper function that compares between two WWeb versions. Its purpose is to help the developer to choose the correct code implementation depending on the comparison value and the WWeb version.
* @param {string} lOperand The left operand for the WWeb version string to compare with
* @param {string} operator The comparison operator
* @param {string} rOperand The right operand for the WWeb version string to compare with
* @returns {boolean} Boolean value that indicates the result of the comparison
*/
window.compareWwebVersions = (lOperand, operator, rOperand) => {
if (!['>', '>=', '<', '<=', '='].includes(operator)) {
throw new class _ extends Error {
constructor(m) { super(m); this.name = 'CompareWwebVersionsError'; }
}('Invalid comparison operator is provided');
}
if (typeof lOperand !== 'string' || typeof rOperand !== 'string') {
throw new class _ extends Error {
constructor(m) { super(m); this.name = 'CompareWwebVersionsError'; }
}('A non-string WWeb version type is provided');
}
lOperand = lOperand.replace(/-beta$/, '');
rOperand = rOperand.replace(/-beta$/, '');
while (lOperand.length !== rOperand.length) {
lOperand.length > rOperand.length
? rOperand = rOperand.concat('0')
: lOperand = lOperand.concat('0');
}
lOperand = Number(lOperand.replace(/\./g, ''));
rOperand = Number(rOperand.replace(/\./g, ''));
return (
operator === '>' ? lOperand > rOperand :
operator === '>=' ? lOperand >= rOperand :
operator === '<' ? lOperand < rOperand :
operator === '<=' ? lOperand <= rOperand :
operator === '=' ? lOperand === rOperand :
false
);
};
if (!window.decodeBackStanza) {
window.decodeBackStanza = (window.mR.findModule('decodeStanza')[0]).decodeStanza;
window.encodeBackStanza = (window.mR.findModule('encodeStanza')[0]).encodeStanza;
}
(window.mR.findModule('decodeStanza')[0]).decodeStanza = async (e, t) => {
const result = await window.decodeBackStanza(e, t);
console.log('[INFO] coming from whatsapp, tag:' + result.tag + ' , xmlns:' + result.attrs?.xmlns + ' , type:' + result.attrs?.type, result);
return result;
}
(window.mR.findModule('encodeStanza')[0]).encodeStanza = (...args) => {
const result = window.encodeBackStanza(...args);
console.log('[INFO] going to whatsapp, tag:' + args[0].tag + ' , xmlns:' + args[0].attrs?.xmlns + ' , type:' + args[0].attrs?.type, args[0]);
return result;
}
@PurpShell
Copy link
Author

To use this tool, just copy the code in here and paste it to the console. You can also use Code Injector.

If you found some use out of this, please donate. :D

@andresayac
Copy link

It is possible that it is missing a } since I see a syntax error, but it is great, I have checked it

@PurpShell
Copy link
Author

PurpShell commented Jun 20, 2024

Please use the new tool for 2.3000x and above: https://gist.github.com/PurpShell/13f198b996b46e3e783bee1ef06d1a35

@A-d-i-t-h-y-a-n
Copy link

VM513:69 Uncaught TypeError: Cannot read properties of undefined (reading 'default')
at :69:95

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment