NestJS module for the WhatsApp Cloud API. Supports sandbox & live modes, webhooks, microservice transport, Prometheus metrics, and health checks.
{ mediaId } or fresh media via URL string / { url }WhatsAppMode — safe, type-checked client selectionWhatsAppEvents — subscribe to text, image, audio, video, reactions, referrals (Click-to-WhatsApp) and moreWhatsAppMediaService, WhatsAppTemplatesService, WhatsAppPhoneNumbersServicenest-whatsapp/metrics) and Nest Terminus health indicator (nest-whatsapp/health) — opt-in sub-entries, zero overhead when unusedforMicroservicenest generate whatsappnpm install nest-whatsapp
// app.module.ts
import { Module } from '@nestjs/common';
import { ConfigModule, ConfigService } from '@nestjs/config';
import { WhatsAppModule, WhatsAppMode } from 'nest-whatsapp';
@Module({
imports: [
ConfigModule.forRoot({ isGlobal: true }),
WhatsAppModule.forRootAsync({
imports: [ConfigModule],
inject: [ConfigService],
useFactory: (cs: ConfigService) => {
const mode = cs.get('WHATSAPP_MODE');
if (mode === 'sandbox') {
return {
mode: WhatsAppMode.SANDBOX,
testPhoneNumberId: cs.getOrThrow('WHATSAPP_SANDBOX_PHONE_NUMBER_ID'),
temporaryAccessToken: cs.getOrThrow('WHATSAPP_SANDBOX_ACCESS_TOKEN'),
testRecipients: cs.get<string>('WHATSAPP_SANDBOX_TEST_RECIPIENTS')?.split(',') ?? [],
};
}
return {
mode: WhatsAppMode.LIVE,
businessAccountId: cs.getOrThrow('WHATSAPP_LIVE_BUSINESS_ACCOUNT_ID'),
phoneNumberId: cs.getOrThrow('WHATSAPP_LIVE_PHONE_NUMBER_ID'),
accessToken: cs.getOrThrow('WHATSAPP_LIVE_ACCESS_TOKEN'),
};
},
}),
],
})
export class AppModule {}
// notification.service.ts
import { Injectable } from '@nestjs/common';
import { WhatsAppService, WhatsAppMode } from 'nest-whatsapp';
@Injectable()
export class NotificationService {
constructor(private readonly wa: WhatsAppService) {}
async sendWelcome(to: string) {
// Templates can be sent at any time — no prior conversation required
await this.wa.sendTemplate(to, 'welcome', [], WhatsAppMode.LIVE);
}
async reply(to: string, text: string, originalMessageId: string) {
// Free-form text requires the user to have messaged you first (24h window)
await this.wa.sendText(to, text, WhatsAppMode.LIVE, originalMessageId);
}
}
⚠️ 24-hour window: WhatsApp only allows free-form text messages when the user has contacted you within the last 24 hours. Use
sendTemplateto initiate conversations. See Sending Messages for details.
| Guide | Contents |
|---|---|
| Getting Started | Installation, forRoot / forRootAsync, env vars, multi-client setup |
| Configuration | All env variables, runtime options, per-client HTTP overrides, Joi schema |
| Sending Messages | All 12 send methods with code examples, 24h window, reply threading |
| Webhooks & Events | Bootstrap setup, WhatsAppEvents, all event types, security |
| Modes: Sandbox vs Live | WhatsAppMode enum, testRecipients allow-list, multi-mode |
| Advanced | Metrics, health, microservice, media/templates/phone management, schematics |
Apache-2.0