// core/index.js const websocketServicesI = require('./websocket/services/session'); const websocketConnectionI = require('./websocket/connection'); // Create the instances here const websocketService = websocketServicesI(); const websocketManager = websocketConnectionI(websocketService); const { makeWASocket, WAProto, DisconnectReason, fetchLatestBaileysVersion, makeCacheableSignalKeyStore, makeInMemoryStore, useMultiFileAuthState, downloadMediaMessage } = require('@whiskeysockets/baileys'); const { writeFile } = require('fs/promises'); const NodeCache = require('node-cache'); const P = require('pino'); const logger = P({ timestamp: () => `,"time":"${new Date().toJSON()}"` }, P.destination('./wa-logs.txt')) logger.level = 'trace' // external map to store retry counts of messages when decryption/encryption fails // keep this out of the socket itself, so as to prevent a message decryption/encryption loop across socket restarts const msgRetryCounterCache = new NodeCache() // the store maintains the data of the WA connection in memory // can be written out to a file & read from it const store = makeInMemoryStore({ logger }) store?.readFromFile('./baileys_store_multi.json') // save every 10s setInterval(() => { store?.writeToFile('./baileys_store_multi.json') }, 10_000) // start a connection const createWhatsApp = async (channelId, phone) => { const { state, saveCreds } = await useMultiFileAuthState('baileys_auth_info_' + channelId + '_' + phone) // fetch latest version of WA Web const { version, isLatest } = await fetchLatestBaileysVersion() const waVersion = version.join('.') + ', ' + (isLatest ? 'latest' : 'out') return new Promise((resolve, reject) => { const sendTextMessage = (whatsAppNo, content) => { sock.sendMessage(whatsAppNo + '@s.whatsapp.net', { text: content }) } const sendImageMessage = (whatsAppNo, imageUrl) => { sock.sendMessage(whatsAppNo + '@s.whatsapp.net', { image: { url: imageUrl}, }) } const sock = makeWASocket({ version, logger, auth: { creds: state.creds, /** caching makes the store faster to send/recv messages */ keys: makeCacheableSignalKeyStore(state.keys, logger), }, msgRetryCounterCache, generateHighQualityLinkPreview: true, }) // something about the connection changed // maybe it closed, or we received all offline message or connection opened sock.ev.on('connection.update', async (update) => { console.log('connection update: ', update) const { connection, lastDisconnect, qr } = update if(connection === 'close') { console.log('链接断开:', lastDisconnect) if (lastDisconnect?.error?.output?.statusCode !== DisconnectReason.loggedOut) { createWhatsApp(channelId, phone) } else { sock.end((error) => console.error('end.error: ', error)) sock.logout((msg) => console.error('logout.msg: ', msg)) console.log('Connection closed. You are logged out.') reject('Connection closed. You are logged out.') } } else if(connection === 'open') { console.info('链接成功') await sock.sendMessage('8617607730395' + '@s.whatsapp.net', { text: 'OPEN: ' + new Date().toString() }) } else if(qr !== undefined) { // WebSocket 创建成功等待扫码,如果没有扫码会更新 qr resolve({ qrCode: qr, version: waVersion, createTimestamp: Date.now(), status: 'connecting', channelId : channelId, phone: phone, ...sendTextMessage, ...sendImageMessage }) } }) sock.ev.on('messages.upsert', async (upsert) => { console.log('收到消息:', JSON.stringify(upsert, undefined, 2)) if (upsert.type === 'notify') { for (const msg of upsert.messages) { const messageType = Object.keys(msg.message)[0] console.log('messageType', messageType) if (messageType === 'imageMessage') { // download the message const buffer = await downloadMediaMessage( msg, 'buffer', { }, { logger, // pass this so that baileys can request a reupload of media // that has been deleted reuploadRequest: sock.updateMediaMessage } ) // save to file await writeFile('d:/my-download.jpeg', buffer) console.log('writeFile', messageType) } const fromWhatsAppNo = msg.key.remoteJid.split('@')[0] if (msg.message?.conversation || msg.message?.extendedTextMessage?.text) { const text = msg.message?.conversation || msg.message?.extendedTextMessage?.text if (text.indexOf('图片') > -1){ sendImageMessage(fromWhatsAppNo, 'https://images.asiahighlights.com/allpicture/2022/07/8a7d9ced5936463bb904c82a_cut_750x850_349.webp') } else if (text.indexOf('文本') > -1){ sendTextMessage(fromWhatsAppNo, '文本消息' + new Date().toString()) } } } } }) // 不绑定不会影响扫码登录 store?.bind(sock.ev) // the process function lets you process all events that just occurred // efficiently in a batch sock.ev.process( // events is a map for event name => event data async (events) => { // credentials updated -- save them if (events['creds.update']) { await saveCreds() } }, ) }) } module.exports = { websocketService, websocketManager, createWhatsApp, };