Bot WA Multi-Admin & Multi-Device
Cara setup bot WhatsApp untuk banyak admin. Koordinasi tim CS, assignment chat, multi-device. Kolaborasi tim lebih efektif!
Satu nomor WA, dihandle banyak admin!
Bisnis yang grow butuh tim CS, bukan satu orang. Bot multi-admin memungkinkan kolaborasi tim yang efektif.
Kapan Butuh Multi-Admin?
📈 TANDA-TANDA BUTUH MULTI-ADMIN:
- Chat queue menumpuk
- Response time >15 menit
- Satu admin kewalahan
- Ada shift pagi/siang/malam
- Perlu spesialisasi (sales/support)
- Tim remote di lokasi berbedaArsitektur Multi-Admin
┌─────────────────────────────────────────────┐
│ 1 NOMOR WHATSAPP │
│ (Business Number) │
└────────────────────┬────────────────────────┘
│
▼
┌─────────────────────────────────────────────┐
│ BOT SERVER │
│ (Central Controller) │
└────────────────────┬────────────────────────┘
│
┌────────────┼────────────┐
▼ ▼ ▼
┌──────────────┐ ┌──────────────┐ ┌──────────────┐
│ ADMIN 1 │ │ ADMIN 2 │ │ ADMIN 3 │
│ (Dashboard) │ │ (Dashboard) │ │ (Dashboard) │
│ Shift Pagi │ │ Shift Siang │ │ Shift Malam │
└──────────────┘ └──────────────┘ └──────────────┘Multi-Device WhatsApp
Kapasitas Linked Devices:
📱 WHATSAPP MULTI-DEVICE:
Primary: 1 HP (wajib)
Linked Devices: Max 4
- WhatsApp Web browser
- WhatsApp Desktop
- Bot server
- Device lain
Total: 5 devices simultanSetup Linked Device untuk Admin:
Cara link device baru:
1. Admin buka web.whatsapp.com
2. Pemilik nomor: Settings → Linked Devices
3. Tap "Link a Device"
4. Scan QR code
5. Done! Admin bisa akses
⚠️ Limit: 4 linked devices
Jika perlu lebih, pertimbangkan Cloud APIStrategi Assignment Chat
1. Round Robin (Bergiliran):
javascript
const admins = ['admin1', 'admin2', 'admin3'];
let currentIndex = 0;
function assignChat(chatId) {
const assignedAdmin = admins[currentIndex];
currentIndex = (currentIndex + 1) % admins.length;
return assignedAdmin;
}
// Chat 1 → admin1
// Chat 2 → admin2
// Chat 3 → admin3
// Chat 4 → admin1 (cycle)2. Load Balancing (by workload):
javascript
const adminWorkload = {
admin1: 0,
admin2: 0,
admin3: 0
};
function assignChatByLoad(chatId) {
// Find admin with lowest workload
const assignedAdmin = Object.entries(adminWorkload)
.sort(([,a], [,b]) => a - b)[0][0];
adminWorkload[assignedAdmin]++;
return assignedAdmin;
}
// Selalu assign ke yang paling sedikit kerjaan3. Skill-Based Routing:
javascript
const adminSkills = {
admin1: ['sales', 'product'],
admin2: ['support', 'complaint'],
admin3: ['technical', 'refund']
};
function assignBySkill(chatId, intent) {
for (const [admin, skills] of Object.entries(adminSkills)) {
if (skills.includes(intent)) {
return admin;
}
}
return 'admin1'; // default
}
// "Mau beli" → admin1 (sales)
// "Barang rusak" → admin2 (complaint)
// "Cara pakai?" → admin3 (technical)4. Shift-Based:
javascript
function assignByShift() {
const hour = new Date().getHours();
if (hour >= 8 && hour < 16) {
return 'admin_pagi'; // 08:00 - 16:00
} else if (hour >= 16 && hour < 24) {
return 'admin_siang'; // 16:00 - 24:00
} else {
return 'admin_malam'; // 00:00 - 08:00 (atau bot only)
}
}Implementasi Multi-Admin
Database Struktur:
javascript
// Chat assignments
const chatAssignments = {
'628123456789': {
assignedTo: 'admin1',
assignedAt: '2026-02-17T10:00:00Z',
status: 'active', // active, resolved, pending
lastActivity: '2026-02-17T10:05:00Z'
}
};
// Admin status
const adminStatus = {
admin1: {
name: 'Ani',
status: 'online', // online, busy, offline
currentChats: 5,
maxChats: 10,
shift: 'pagi'
}
};Assignment Logic:
javascript
client.on('message', async msg => {
const chatId = msg.from;
// Check existing assignment
let assignment = await db.assignments.findOne({ chatId });
if (!assignment) {
// New chat, assign to available admin
const availableAdmin = await findAvailableAdmin();
assignment = {
chatId,
assignedTo: availableAdmin,
assignedAt: new Date(),
status: 'active'
};
await db.assignments.insert(assignment);
// Notify admin
await notifyAdmin(availableAdmin, `New chat assigned: ${chatId}`);
}
// Forward to assigned admin's dashboard
await forwardToAdminDashboard(assignment.assignedTo, msg);
});Transfer Chat:
javascript
// Admin bisa transfer chat ke admin lain
async function transferChat(chatId, fromAdmin, toAdmin, reason) {
await db.assignments.updateOne(
{ chatId },
{
$set: {
assignedTo: toAdmin,
transferredFrom: fromAdmin,
transferReason: reason,
transferredAt: new Date()
}
}
);
// Notify both admins
await notifyAdmin(fromAdmin, `Chat transferred to ${toAdmin}`);
await notifyAdmin(toAdmin, `New chat transferred from ${fromAdmin}: ${chatId}`);
// Notify customer (optional)
await sendToCustomer(chatId,
'Chat kakak akan dilanjutkan oleh tim kami yang lain ya! 🙏'
);
}Dashboard Admin
Fitur Dashboard:
📊 ADMIN DASHBOARD
┌─────────────────────────────────────┐
│ Welcome, Admin Ani! │
│ Status: 🟢 Online │
│ Active Chats: 5/10 │
└─────────────────────────────────────┘
┌─────────────────────────────────────┐
│ 📥 CHAT QUEUE │
│ │
│ 🔴 Customer A (waiting 5m) │
│ 🟡 Customer B (waiting 2m) │
│ 🟢 Customer C (just arrived) │
└─────────────────────────────────────┘
┌─────────────────────────────────────┐
│ 💬 ACTIVE CHATS │
│ │
│ • Customer D - Asking price │
│ • Customer E - Complaint │
│ • Customer F - Order status │
└─────────────────────────────────────┘
[Take Chat] [Transfer] [Resolve]Simple Web Dashboard:
javascript
// Express.js dashboard
app.get('/dashboard/:adminId', async (req, res) => {
const { adminId } = req.params;
const activeChats = await db.assignments.find({
assignedTo: adminId,
status: 'active'
});
const queuedChats = await db.assignments.find({
status: 'pending'
});
res.render('dashboard', {
admin: adminId,
activeChats,
queuedChats
});
});Koordinasi Tim
Handover Antar Shift:
javascript
// Saat admin logout, reassign chat-nya
async function adminLogout(adminId) {
const activeChats = await db.assignments.find({
assignedTo: adminId,
status: 'active'
});
for (const chat of activeChats) {
// Find next available admin
const nextAdmin = await findAvailableAdmin();
if (nextAdmin) {
await transferChat(chat.chatId, adminId, nextAdmin, 'shift_handover');
} else {
// No admin available, mark as pending
await db.assignments.updateOne(
{ chatId: chat.chatId },
{ $set: { status: 'pending' } }
);
}
}
await db.admins.updateOne(
{ id: adminId },
{ $set: { status: 'offline' } }
);
}Internal Notes:
javascript
// Admin bisa tinggalkan notes untuk tim
async function addInternalNote(chatId, adminId, note) {
await db.chatNotes.insert({
chatId,
adminId,
note,
createdAt: new Date()
});
}
// Notes visible di dashboard:
// "Customer ini sudah komplain 2x sebelumnya - handle carefully"
// "Mau bayar tapi tunggu gajian tanggal 25"Best Practices
DO ✅
- Clear assignment rules
- Real-time sync antar admin
- Internal notes system
- Handover protocol
- Performance tracking
- Customer tidak perlu tahu ganti adminDON'T ❌
- Dua admin reply customer yang sama
- Chat tidak ada yang handle
- Tidak ada handover saat ganti shift
- Customer di-ping-pong antar admin
- Tidak ada history percakapanMetrics & KPI
📊 TRACK PERFORMANCE:
Per Admin:
- Jumlah chat handled/hari
- Average response time
- Resolution rate
- Customer satisfaction
Tim:
- Total chat volume
- Peak hours
- Queue wait time
- Transfer rateFAQ
Bisa lebih dari 4 linked devices?
Dengan WhatsApp biasa, tidak. Jika butuh lebih, gunakan WhatsApp Cloud API yang tidak ada limit device.
Bagaimana avoid double reply?
Locking system: Saat admin buka chat, lock untuk admin lain. Atau assignment yang jelas sejak awal.
Customer tau ganti admin?
Seharusnya tidak perlu tau, kecuali memang mau transparansi. Smooth handover tanpa bilang ke customer.
Kesimpulan
Multi-admin = Scalable customer service!
| Single Admin | Multi-Admin |
|---|---|
| Overload | Distributed workload |
| Limited hours | 24/7 coverage |
| Single point of failure | Team redundancy |
| No specialization | Skill-based routing |
Scale your team, scale your service!