Skip to main content

What is Storage?

The WhatsApp Client SDK includes a powerful storage system that automatically persists incoming and outgoing messages to a database. This enables you to:
  • ๐Ÿ“Š Query conversation history - Retrieve past messages and conversations
  • ๐Ÿ” Search messages - Full-text search across all messages
  • ๐Ÿ“ˆ Analytics - Track conversation metrics and patterns
  • ๐Ÿ’พ Data retention - Automatic cleanup of old messages
  • ๐Ÿงต Thread tracking - Follow message reply chains

Key Features

Automatic Persistence

Messages are automatically saved to your database without additional code

Full-Text Search

Search through all messages with powerful query capabilities

Conversation Analytics

Track message counts, response rates, and engagement metrics

Data Export

Export conversations in JSON or CSV format for analysis

Thread Tracking

Automatically track message replies and conversation threads

Flexible Retention

Configure automatic deletion of old messages based on your needs

How It Works

1. Enable Storage

Configure storage when initializing the WhatsApp client:
import { WhatsAppClient } from 'whatsapp-client-sdk';

const client = new WhatsAppClient({
  accessToken: process.env.WHATSAPP_ACCESS_TOKEN!,
  phoneNumberId: process.env.WHATSAPP_PHONE_NUMBER_ID!,

  // Enable storage
  storage: {
    enabled: true,
    provider: 'supabase',
    options: {
      url: process.env.SUPABASE_URL!,
      apiKey: process.env.SUPABASE_KEY!
    },
    features: {
      persistIncoming: true,
      persistOutgoing: true,
      persistStatus: true,
      autoConversations: true
    }
  }
});

// Initialize storage
await client.initializeStorage();

2. Messages Are Saved Automatically

Once storage is enabled, all messages are automatically persisted:
// Incoming messages are saved automatically via webhooks
const webhookProcessor = client.createWebhookProcessor({
  onTextMessage: async (message) => {
    // Message is already saved to database
    await client.sendText(message.from, 'Got your message!');
    // Response is also saved automatically
  }
});

// Outgoing messages are saved when sent
await client.sendText('+1234567890', 'Hello!');
// Saved to database automatically

3. Query Your Data

Use the built-in query methods:
// Get conversation history
const conversation = await client.getConversation('+1234567890', {
  limit: 50
});

// Search messages
const results = await client.searchMessages({
  text: 'order',
  phoneNumber: '+1234567890'
});

// Get analytics
const analytics = await client.getConversationAnalytics('+1234567890');

Storage Providers

Supabase is the primary storage provider with full support for all features:
  • โœ… PostgreSQL-backed
  • โœ… Real-time subscriptions
  • โœ… Built-in authentication
  • โœ… Auto-generated APIs
  • โœ… Free tier available

Supabase Integration Guide

Complete setup guide for Supabase storage

Custom Adapters

You can implement your own storage adapter for other databases:

Custom Storage Adapters

Learn how to create custom storage adapters

Storage Configuration

Feature Flags

Control what data is persisted:
storage: {
  enabled: true,
  provider: 'supabase',
  options: { /* ... */ },
  features: {
    persistIncoming: true,   // Save incoming messages
    persistOutgoing: true,   // Save outgoing messages
    persistStatus: true,     // Update message status (sent, delivered, read)
    autoConversations: true, // Auto-create conversations
    createThreads: true,     // Track message threads/replies
    enableSearch: true,      // Enable full-text search
    retentionDays: 90       // Auto-delete messages after 90 days
  }
}

Data Retention

Automatically clean up old messages:
// Configure automatic cleanup
features: {
  retentionDays: 90  // Delete messages older than 90 days
}

// Or manually trigger cleanup
const deletedCount = await client.cleanupOldMessages();
console.log(`Deleted ${deletedCount} old messages`);

Use Cases

Customer Support

Track support conversations and response times:
// Get customer conversation history
const history = await client.getConversation(customerPhone);

// Analyze response patterns
const analytics = await client.getConversationAnalytics(customerPhone, {
  from: new Date('2024-01-01'),
  to: new Date()
});

console.log(`Average response time: ${analytics.averageResponseTime}ms`);
console.log(`Total conversations: ${analytics.totalMessages}`);

E-commerce

Search order-related messages:
// Find all messages about a specific order
const orderMessages = await client.searchMessages({
  text: 'ORDER-12345',
  dateFrom: new Date('2024-01-01')
});

// Export for analysis
const exportData = await client.exportConversation(customerPhone, {
  format: 'json'
});

Compliance & Auditing

Maintain message records for compliance:
// Export conversation for audit trail
const auditLog = await client.exportConversation('+1234567890', {
  format: 'csv',
  dateFrom: new Date('2024-01-01'),
  dateTo: new Date('2024-12-31')
});

// Save to compliance system
await saveToComplianceSystem(auditLog);

Performance Considerations

Indexing

Storage providers automatically create indexes on:
  • Phone numbers
  • Message timestamps
  • Message types
  • Status fields

Pagination

Always use pagination for large datasets:
// Good: Paginated queries
const page1 = await client.getConversation(phone, { limit: 50, offset: 0 });
const page2 = await client.getConversation(phone, { limit: 50, offset: 50 });

// Avoid: Loading all messages at once
const allMessages = await client.getConversation(phone, { limit: 10000 });

Caching

Implement caching for frequently accessed data:
const cache = new Map();

async function getCachedConversation(phone: string) {
  if (cache.has(phone)) {
    return cache.get(phone);
  }

  const conversation = await client.getConversation(phone);
  cache.set(phone, conversation);

  // Cache for 5 minutes
  setTimeout(() => cache.delete(phone), 5 * 60 * 1000);

  return conversation;
}

Security

Access Control

  • Use service role keys only in backend code
  • Never expose database credentials in frontend
  • Implement Row Level Security (RLS) in Supabase

Data Privacy

  • Hash or encrypt sensitive message content
  • Implement data retention policies
  • Provide user data export/deletion capabilities

Storage Best Practices

Learn security and performance best practices

Next Steps

โŒ˜I