fix: typing indicator now shows on every message, not just the first
Two issues fixed:
- Use 'paused' instead of 'available' to stop typing. Baileys'
sendPresenceUpdate('available') sends a global <presence> stanza and
ignores the JID, so chatstate never left 'composing' and WhatsApp
suppressed duplicate composing notifications per XEP-0085.
- Add setTyping call when piping messages to an already-running
container. Previously only the first message (which spawns a new
container) triggered the typing indicator.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -823,14 +823,14 @@ describe('WhatsAppChannel', () => {
|
|||||||
expect(fakeSocket.sendPresenceUpdate).toHaveBeenCalledWith('composing', 'test@g.us');
|
expect(fakeSocket.sendPresenceUpdate).toHaveBeenCalledWith('composing', 'test@g.us');
|
||||||
});
|
});
|
||||||
|
|
||||||
it('sends available presence when stopping', async () => {
|
it('sends paused presence when stopping', async () => {
|
||||||
const opts = createTestOpts();
|
const opts = createTestOpts();
|
||||||
const channel = new WhatsAppChannel(opts);
|
const channel = new WhatsAppChannel(opts);
|
||||||
|
|
||||||
await connectChannel(channel);
|
await connectChannel(channel);
|
||||||
|
|
||||||
await channel.setTyping('test@g.us', false);
|
await channel.setTyping('test@g.us', false);
|
||||||
expect(fakeSocket.sendPresenceUpdate).toHaveBeenCalledWith('available', 'test@g.us');
|
expect(fakeSocket.sendPresenceUpdate).toHaveBeenCalledWith('paused', 'test@g.us');
|
||||||
});
|
});
|
||||||
|
|
||||||
it('handles typing indicator failure gracefully', async () => {
|
it('handles typing indicator failure gracefully', async () => {
|
||||||
|
|||||||
@@ -218,7 +218,9 @@ export class WhatsAppChannel implements Channel {
|
|||||||
|
|
||||||
async setTyping(jid: string, isTyping: boolean): Promise<void> {
|
async setTyping(jid: string, isTyping: boolean): Promise<void> {
|
||||||
try {
|
try {
|
||||||
await this.sock.sendPresenceUpdate(isTyping ? 'composing' : 'available', jid);
|
const status = isTyping ? 'composing' : 'paused';
|
||||||
|
logger.debug({ jid, status }, 'Sending presence update');
|
||||||
|
await this.sock.sendPresenceUpdate(status, jid);
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
logger.debug({ jid, err }, 'Failed to update typing status');
|
logger.debug({ jid, err }, 'Failed to update typing status');
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -360,6 +360,8 @@ async function startMessageLoop(): Promise<void> {
|
|||||||
lastAgentTimestamp[chatJid] =
|
lastAgentTimestamp[chatJid] =
|
||||||
messagesToSend[messagesToSend.length - 1].timestamp;
|
messagesToSend[messagesToSend.length - 1].timestamp;
|
||||||
saveState();
|
saveState();
|
||||||
|
// Show typing indicator while the container processes the piped message
|
||||||
|
whatsapp.setTyping(chatJid, true);
|
||||||
} else {
|
} else {
|
||||||
// No active container — enqueue for a new one
|
// No active container — enqueue for a new one
|
||||||
queue.enqueueMessageCheck(chatJid);
|
queue.enqueueMessageCheck(chatJid);
|
||||||
|
|||||||
Reference in New Issue
Block a user