Bot Jualan untuk Flash Sale & Limited Stock

Cara buat bot jualan WhatsApp untuk flash sale. Countdown, limited stock, queue system. Handle rush tanpa crash!

Bot Jualan untuk Flash Sale & Limited Stock
Bot Jualan untuk Flash Sale & Limited Stock

Flash sale = High pressure selling!

Bot yang siap flash sale harus bisa handle surge traffic, real-time stock, dan create urgency yang convert.


Flash Sale Challenges

🔥 TANTANGAN:

- Traffic 10-50x normal
- Stock harus real-time accurate
- Race condition (oversell risk)
- Customer frustration
- Bot overload

✅ SOLUSI:

- Queue system
- Stock locking
- Real-time updates
- Urgency messaging
- Scalable infrastructure

Template Messages

Flash Sale Announcement:

🔥 FLASH SALE ALERT!

[PRODUCT NAME]

HARGA NORMAL: ~Rp 500.000~
FLASH PRICE: Rp 250.000 (50% OFF!)

📦 Stok: HANYA 50 PCS!
⏰ Mulai: HARI INI, 20:00 WIB

Set alarm sekarang! ⏰

Reply REMIND untuk dapat reminder
5 menit sebelum flash sale!

🔔 Siap-siap rebutan! 🔥

Reminder:

⏰ REMINDER: 5 MENIT LAGI!

🔥 FLASH SALE dimulai 20:00 WIB!

[PRODUCT NAME]
💰 Rp 250.000 (50% OFF!)
📦 Stok: 50 pcs

⚡ TIPS CEPAT:
1. Siapkan alamat pengiriman
2. Langsung ketik: BELI [NAMA]
3. Konfirmasi dalam 5 menit

Ketik BELI [PRODUK] tepat jam 20:00!

Good luck! 🍀

Flash Sale Live:

🔥 FLASH SALE LIVE!

[PRODUCT NAME] - Rp 250.000

📦 STOK TERSISA: 47/50

⚡ ORDER SEKARANG!
Ketik: FLASH [JUMLAH]
Contoh: FLASH 2

⏱️ Keranjang berlaku 5 menit!
Bayar langsung untuk amankan.

Cepat sebelum kehabisan! 🏃‍♂️

Stock Update (Real-time):

📦 UPDATE STOK

[PRODUCT NAME]

TERSISA: 23 pcs! 🔥🔥🔥

Terjual: 27 pcs dalam 3 menit!

Belum order?
Ketik FLASH [JUMLAH] sekarang!

⚠️ Stok menipis sangat cepat!

Queue System:

⏳ ANTRIAN FLASH SALE

Hai! Karena traffic tinggi,
kakak masuk antrian.

📊 Status:
━━━━━━━━━━━━━━━━━━━━
Posisi: #127
Estimasi: 2 menit
Stok saat ini: 35 pcs
━━━━━━━━━━━━━━━━━━━━

Jangan close chat ini!
Kami akan notify saat giliran.

💡 Tip: Siapkan alamat & pembayaran!

Your Turn:

🎉 GILIRAN KAKAK!

Stok tersisa: 28 pcs
Waktu order: 3 menit!

⚡ KONFIRMASI ORDER:
━━━━━━━━━━━━━━━━━━━━
Produk: [NAMA]
Harga: Rp 250.000
Qty: 1 (max 2)
━━━━━━━━━━━━━━━━━━━━

Ketik OK untuk lanjut checkout!
Atau ketik QTY [JUMLAH] untuk ubah.

⏱️ 03:00 tersisa...

Cart Reserved:

🔒 STOK DIAMANKAN!

Produk sudah di-lock untuk kakak!

📋 Order:
━━━━━━━━━━━━━━━━━━━━
[PRODUCT] x 2
Harga: Rp 500.000
━━━━━━━━━━━━━━━━━━━━

⏱️ BAYAR DALAM: 05:00

💳 Link pembayaran:
[PAYMENT LINK]

⚠️ Stok akan dilepas
   jika tidak bayar dalam 5 menit!

Bayar sekarang! 💨

Sold Out:

😢 SOLD OUT!

Maaf, [PRODUCT] sudah HABIS!

Terjual: 50 pcs dalam 8 menit! 🔥

Jangan sedih! Pilihan untuk kakak:

1️⃣ NOTIFY ME
   Dapat notif kalau restock

2️⃣ SIMILAR PRODUCTS
   Lihat produk serupa

3️⃣ NEXT FLASH SALE
   Info flash sale berikutnya

Ketik angka untuk pilih!

Terima kasih sudah ikutan! 🙏

Implementation

Stock Locking:

javascript

const redis = require('redis');
const client = redis.createClient();

async function lockStock(productId, quantity, sessionId) {
    const stockKey = `stock:${productId}`;
    const lockKey = `lock:${productId}:${sessionId}`;
    
    // Use Redis transaction for atomicity
    const multi = client.multi();
    
    // Check current stock
    const currentStock = await client.get(stockKey);
    
    if (parseInt(currentStock) < quantity) {
        return { success: false, reason: 'insufficient_stock' };
    }
    
    // Decrement stock
    multi.decrby(stockKey, quantity);
    
    // Set lock with expiry (5 minutes)
    multi.setex(lockKey, 300, JSON.stringify({
        quantity,
        lockedAt: Date.now()
    }));
    
    await multi.exec();
    
    return { 
        success: true, 
        lockId: lockKey,
        expiresIn: 300
    };
}

async function releaseStock(productId, sessionId, quantity) {
    const stockKey = `stock:${productId}`;
    const lockKey = `lock:${productId}:${sessionId}`;
    
    // Check if lock exists
    const lock = await client.get(lockKey);
    
    if (lock) {
        // Return stock
        await client.incrby(stockKey, quantity);
        await client.del(lockKey);
    }
}

// Auto-release expired locks
setInterval(async () => {
    const expiredLocks = await findExpiredLocks();
    
    for (const lock of expiredLocks) {
        await releaseStock(lock.productId, lock.sessionId, lock.quantity);
        await notifyCustomerExpired(lock.phone);
    }
}, 10000); // Check every 10 seconds

Queue System:

javascript

const queue = [];
let processing = false;

async function addToQueue(phone, productId, quantity) {
    const position = queue.length + 1;
    
    queue.push({
        phone,
        productId,
        quantity,
        addedAt: Date.now()
    });
    
    // Notify customer
    await sendQueueMessage(phone, position);
    
    // Start processing if not already
    if (!processing) {
        processQueue();
    }
    
    return position;
}

async function processQueue() {
    processing = true;
    
    while (queue.length > 0) {
        const customer = queue.shift();
        
        // Check stock still available
        const stock = await getStock(customer.productId);
        
        if (stock >= customer.quantity) {
            // Customer's turn
            await sendYourTurnMessage(customer.phone, stock);
            
            // Wait for response (with timeout)
            const response = await waitForResponse(customer.phone, 180000); // 3 min
            
            if (response === 'confirm') {
                await lockStock(customer.productId, customer.quantity, customer.phone);
            }
        } else {
            // No stock left
            await sendSoldOutMessage(customer.phone);
        }
        
        // Small delay between processing
        await sleep(500);
    }
    
    processing = false;
}

Real-time Stock Updates:

javascript

// Broadcast stock updates to interested customers
async function broadcastStockUpdate(productId) {
    const stock = await getStock(productId);
    const watchers = await getStockWatchers(productId);
    
    // Determine urgency level
    let message;
    if (stock <= 5) {
        message = `🔴 HAMPIR HABIS! ${stock} pcs tersisa!`;
    } else if (stock <= 20) {
        message = `🟡 Stok menipis: ${stock} pcs tersisa!`;
    } else {
        message = `📦 Stok: ${stock} pcs`;
    }
    
    // Batch send
    for (const watcher of watchers) {
        await sendStockUpdate(watcher.phone, message);
    }
}

// Call this after every sale
async function onSale(productId, quantity) {
    await decrementStock(productId, quantity);
    await broadcastStockUpdate(productId);
}

Countdown Timer

javascript

// Visual countdown in messages
function generateCountdown(endTime) {
    const now = Date.now();
    const remaining = endTime - now;
    
    if (remaining <= 0) return "⏰ WAKTU HABIS!";
    
    const minutes = Math.floor(remaining / 60000);
    const seconds = Math.floor((remaining % 60000) / 1000);
    
    return `⏱️ ${minutes.toString().padStart(2, '0')}:${seconds.toString().padStart(2, '0')}`;
}

// Send countdown updates
async function sendCountdownUpdates(phone, endTime) {
    const intervals = [300, 60, 30, 10]; // seconds before end
    
    for (const secondsBefore of intervals) {
        const sendAt = endTime - (secondsBefore * 1000);
        
        if (sendAt > Date.now()) {
            setTimeout(async () => {
                const countdown = generateCountdown(endTime);
                await sendMessage(phone, `${countdown} tersisa!`);
            }, sendAt - Date.now());
        }
    }
}

Best Practices

DO ✅

- Real-time stock accuracy
- Queue system for fairness
- Time-limited cart holds
- Clear countdown/urgency
- Graceful sold-out handling
- Restock notifications

DON'T ❌

- Oversell (no stock locking)
- No queue (first come chaos)
- Unlimited cart hold time
- Vague stock info
- Crash during rush
- No follow-up for missed

FAQ

Bagaimana prevent oversell?

Stock locking dengan Redis. Atomic operations, automatic release jika tidak bayar.

Queue system perlu?

Sangat recommended untuk fairness dan prevent server overload.

Berapa lama cart hold time?

5-10 menit ideal. Cukup untuk bayar, tidak terlalu lama block stock.


Kesimpulan

Flash sale bot = Speed + Accuracy!

UnpreparedFlash Sale Ready
OversellStock locking
ChaosQueue system
No urgencyCountdown timer
Customer angryFair process

Setup Flash Sale Bot →


Artikel Terkait