Added method to clear chat and star/unstar message

This commit is contained in:
Edgard
2020-12-14 23:01:14 -03:00
committed by Edgard Messias
parent 282fdb1bd3
commit 5a7077c675
3 changed files with 130 additions and 8 deletions

View File

@@ -116,6 +116,66 @@ WAConnectionTest('Misc', conn => {
await delay (2000)
await conn.modifyChat (testJid, ChatModification.unmute)
})
it('should star/unchar messages', async () => {
for (let i = 1; i <= 5; i++) {
await conn.sendMessage(testJid, `Message ${i}`, MessageType.text)
await delay(1000)
}
let response = await conn.loadMessages(testJid, 5)
let starred = response.messages.filter(m => m.starred)
assert.strictEqual(starred.length, 0)
conn.starMessage(response.messages[2].key)
await delay(2000)
conn.starMessage(response.messages[4].key)
await delay(2000)
response = await conn.loadMessages(testJid, 5)
starred = response.messages.filter(m => m.starred)
assert.strictEqual(starred.length, 2)
await delay(2000)
conn.starMessage(response.messages[2].key, 'unstar')
await delay(2000)
response = await conn.loadMessages(testJid, 5)
starred = response.messages.filter(m => m.starred)
assert.strictEqual(starred.length, 1)
})
it('should clear a chat', async () => {
// Uses chat with yourself to avoid losing chats
const selfJid = conn.user.jid
for (let i = 1; i <= 5; i++) {
await conn.sendMessage(selfJid, `Message ${i}`, MessageType.text)
await delay(1000)
}
let response = await conn.loadMessages(selfJid, 50)
const initialCount = response.messages.length
assert.ok(response.messages.length >= 0)
conn.starMessage(response.messages[2].key)
await delay(2000)
conn.starMessage(response.messages[4].key)
await delay(2000)
await conn.modifyChat(selfJid, ChatModification.clear)
await delay(2000)
response = await conn.loadMessages(selfJid, 50)
await delay(2000)
assert.ok(response.messages.length < initialCount)
assert.ok(response.messages.length > 1)
await conn.modifyChat(selfJid, ChatModification.clear, true)
await delay(2000)
response = await conn.loadMessages(selfJid, 50)
assert.strictEqual(response.messages.length, 1)
})
it('should return search results', async () => {
const jids = [null, testJid]
for (let i in jids) {

View File

@@ -1,6 +1,6 @@
import {WAConnection as Base} from './6.MessagesSend'
import { MessageType, WAMessageKey, MessageInfo, WAMessageContent, WAMetric, WAFlag, WANode, WAMessage, WAMessageProto, ChatModification, BaileysError, WAChatIndex } from './Constants'
import { whatsappID, delay, toNumber, unixTimestampSeconds, GET_MESSAGE_ID, WA_MESSAGE_ID, isGroupID } from './Utils'
import { MessageType, WAMessageKey, MessageInfo, WAMessageContent, WAMetric, WAFlag, WANode, WAMessage, WAMessageProto, ChatModification, BaileysError, WAChatIndex, WAChat } from './Constants'
import { whatsappID, delay, toNumber, unixTimestampSeconds, GET_MESSAGE_ID, WA_MESSAGE_ID, isGroupID, newMessagesDB } from './Utils'
import { Mutex } from './Mutex'
export class WAConnection extends Base {
@@ -285,6 +285,38 @@ export class WAConnection extends Base {
}
return result
}
/**
* Star or unstar a message
* @param messageKey key of the message you want to star or unstar
*/
@Mutex (m => m.remoteJid)
async starMessage (messageKey: WAMessageKey, type: 'star' | 'unstar' = 'star') {
const attrs: WANode = [
'chat',
{
jid: messageKey.remoteJid,
type
},
[
['item', {owner: `${messageKey.fromMe}`, index: messageKey.id}, null]
]
]
const result = await this.setQuery ([attrs])
const chat = this.chats.get (whatsappID(messageKey.remoteJid))
if (result.status == 200 && chat) {
const message = chat.messages.get (GET_MESSAGE_ID(messageKey))
if (message) {
message.starred = type === 'star'
const chatUpdate: Partial<WAChat> = { jid: messageKey.remoteJid, messages: newMessagesDB([ message ]) }
this.emit ('chat-update', chatUpdate)
// emit deprecated
this.emit ('message-update', message)
}
}
return result
}
/**
* Delete a message in a chat for everyone
* @param id the person or group where you're trying to delete the message
@@ -344,25 +376,39 @@ export class WAConnection extends Base {
deleteChat (jid: string) {
return this.modifyChat(jid, 'delete')
}
/**
* Clear the chat messages
* @param jid the ID of the person/group you are modifiying
* @param includeStarred delete starred messages, default false
*/
async modifyChat (jid: string, type: ChatModification.clear, includeStarred?: boolean): Promise<{status: number;}>;
/**
* Modify a given chat (archive, pin etc.)
* @param jid the ID of the person/group you are modifiying
* @param durationMs only for muting, how long to mute the chat for
*/
async modifyChat (jid: string, type: ChatModification.pin | ChatModification.mute, durationMs: number): Promise<{status: number;}>;
/**
* Modify a given chat (archive, pin etc.)
* @param jid the ID of the person/group you are modifiying
*/
async modifyChat (jid: string, type: ChatModification | (keyof typeof ChatModification)): Promise<{status: number;}>;
@Mutex ((jid, type) => jid+type)
async modifyChat (jid: string, type: ChatModification | (keyof typeof ChatModification), durationMs?: number) {
async modifyChat (jid: string, type: (keyof typeof ChatModification), arg?: number | boolean): Promise<{status: number;}> {
jid = whatsappID (jid)
const chat = this.assertChatGet (jid)
let chatAttrs: Record<string, string> = {jid: jid}
if (type === ChatModification.mute && !durationMs) {
if (type === ChatModification.mute && !arg) {
throw new BaileysError(
'duration must be set to the timestamp of the time of pinning/unpinning of the chat',
{ status: 400 }
)
}
durationMs = durationMs || 0
const durationMs:number = arg as number || 0
const includeStarred:boolean = arg as boolean
let index: WAChatIndex;
switch (type) {
case ChatModification.pin:
case ChatModification.mute:
@@ -375,16 +421,30 @@ export class WAConnection extends Base {
chatAttrs.type = type.replace ('un', '') // replace 'unpin' with 'pin'
chatAttrs.previous = chat[type.replace ('un', '')]
break
case ChatModification.clear:
chatAttrs.type = type
chatAttrs.star = includeStarred ? 'true' : 'false'
index = await this.getChatIndex(jid)
chatAttrs = { ...chatAttrs, ...index }
delete chatAttrs.participant
break
default:
chatAttrs.type = type
const index = await this.getChatIndex(jid)
index = await this.getChatIndex(jid)
chatAttrs = { ...chatAttrs, ...index }
break
}
const response = await this.setQuery ([['chat', chatAttrs, null]], [ WAMetric.chat, WAFlag.ignore ])
if (chat) {
if (chat && response.status === 200) {
if (type === ChatModification.clear) {
if (includeStarred) {
chat.messages.clear ()
} else {
chat.messages = chat.messages.filter(m => m.starred)
}
}
if (type.includes('un')) {
type = type.replace ('un', '') as ChatModification
delete chat[type.replace('un','')]

View File

@@ -219,6 +219,7 @@ export interface WAChat {
/** number of unread messages, is < 0 if the chat is manually marked unread */
count: number
archive?: 'true' | 'false'
clear?: 'true' | 'false'
read_only?: 'true' | 'false'
mute?: string
pin?: string
@@ -321,7 +322,8 @@ export enum ChatModification {
unpin='unpin',
mute='mute',
unmute='unmute',
delete='delete'
delete='delete',
clear='clear'
}
export const HKDFInfoKeys = {
[MessageType.image]: 'WhatsApp Image Keys',