Skip to main content

Pengenalan

Event channel.message_in dipicu ketika pesan diterima dari channel komunikasi manapun (WhatsApp, Telegram, Slack, Instagram, Facebook, dll.).
Event ini adalah webhook paling umum yang akan Anda terima, karena mewakili setiap pesan pelanggan yang masuk.

Trigger Event

Pelanggan mengirim pesan

   Platform CSKU AI

   Trigger webhook channel.message_in

   HTTP POST → URL Webhook Anda

Struktur Payload

{
  "event": "channel.message_in",
  "timestamp": 1738056000,
  "conversation_id": "conv_abc123",
  "conversation_label": "John Doe",
  "need_human": 0,
  "message": {
    "id": "msg_xyz789",
    "sender_name": "John Doe",
    "channel": {
      "id": "channel_merchant_id",
      "name": "WhatsApp Business",
      "engine": "wa"
    },
    "bisnis": {
      "id": "biz_123",
      "name": "My Business"
    },
    "user": {
      "id": "merchant_456",
      "name": "Merchant Name"
    },
    "content": {
      "type": "text",
      "text": "Halo, saya butuh bantuan dengan pesanan saya"
    }
  }
}

Deskripsi Field

Field Root

FieldTipeDeskripsi
eventstringIdentifier event: channel.message_in
timestampintegerUnix timestamp saat event terjadi
conversation_idstringIdentifier percakapan unik
conversation_labelstringNama tampilan percakapan
need_humanintegerFlag (0/1) jika percakapan butuh intervensi manusia
messageobjectDetail pesan (lihat di bawah)

Field Message

FieldTipeDeskripsi
message.idstringIdentifier pesan unik
message.sender_namestringNama pengirim pesan
message.channelobjectInformasi channel (lihat di bawah)
message.bisnisobjectInformasi bisnis (lihat di bawah)
message.userobjectInformasi user merchant (lihat di bawah)
message.contentobjectKonten pesan (lihat di bawah)

Field Channel

FieldTipeDeskripsi
channel.idstringIdentifier unik channel
channel.namestringNama tampilan channel
channel.enginestringTipe engine channel (lihat engine yang didukung)

Engine Channel yang Didukung

EngineChannel
waWhatsApp
telegramTelegram
slackSlack
intercomIntercom
instagramInstagram
facebookFacebook Messenger
Field channel.engine membantu Anda mengidentifikasi platform asal pesan.

Field Bisnis & User

FieldTipeDeskripsi
message.bisnis.idstringID Bisnis
message.bisnis.namestringNama bisnis
message.user.idstringID user merchant
message.user.namestringNama merchant

Field Konten (Pesan Teks)

FieldTipeDeskripsi
message.content.typestringTipe pesan: text, image, video, audio, document
message.content.textstringKonten teks pesan (untuk pesan teks)

Payload Pesan Media

Untuk pesan non-teks, payload mencakup attachments:
{
  "event": "channel.message_in",
  "timestamp": 1738056000,
  "conversation_id": "conv_abc123",
  "conversation_label": "John Doe",
  "need_human": 0,
  "message": {
    "id": "msg_xyz789",
    "sender_name": "John Doe",
    "channel": {
      "id": "channel_merchant_id",
      "name": "WhatsApp Business",
      "engine": "wa"
    },
    "bisnis": {
      "id": "biz_123",
      "name": "My Business"
    },
    "user": {
      "id": "merchant_456",
      "name": "Merchant Name"
    },
    "content": {
      "type": "image",
      "attachments": [
        {
          "url": "https://example.com/media/image123.jpg",
          "mime_type": "image/jpeg"
        }
      ]
    }
  }
}

Field Attachment

FieldTipeDeskripsi
urlstringURL untuk mengakses file media
mime_typestringMIME type file (misal, image/jpeg, video/mp4)

Tipe Media yang Didukung

TipeMIME Types
imageimage/jpeg, image/png, image/gif, image/webp
videovideo/mp4, video/avi, video/mov, video/webm
audioaudio/mp3, audio/wav, audio/ogg, audio/aac
documentapplication/pdf, application/msword, text/plain

Contoh Implementasi

Node.js

app.post('/webhook', async (req, res) => {
  const { event, message } = req.body;
  
  if (event === 'channel.message_in') {
    const { id, sender_name, content, channel } = message;
    
    console.log(`Pesan baru dari ${sender_name}`);
    
    // Tangani pesan teks
    if (content.type === 'text') {
      console.log('Pesan:', content.text);
      // Simpan ke database
      await db.messages.create({
        message_id: id,
        sender: sender_name,
        text: content.text,
        channel: channel.engine
      });
    }
    
    // Tangani pesan media
    if (content.attachments) {
      content.attachments.forEach(attachment => {
        console.log('URL Media:', attachment.url);
        // Download atau proses media
      });
    }
  }
  
  res.status(200).send('OK');
});

Python

@app.route('/webhook', methods=['POST'])
def webhook():
    data = request.get_json()
    event = data.get('event')
    message = data.get('message')
    
    if event == 'channel.message_in':
        msg_id = message['id']
        sender = message['sender_name']
        content = message['content']
        channel = message['channel']
        
        print(f"Pesan baru dari {sender}")
        
        # Tangani pesan teks
        if content['type'] == 'text':
            text = content['text']
            print(f"Pesan: {text}")
            # Simpan ke database
            db.messages.create(
                message_id=msg_id,
                sender=sender,
                text=text,
                channel=channel['engine']
            )
        
        # Tangani pesan media
        if 'attachments' in content:
            for attachment in content['attachments']:
                print(f"URL Media: {attachment['url']}")
    
    return 'OK', 200

Use Case

Trigger respons otomatis atau arahkan ke tim dukungan yang tepat berdasarkan konten pesan.
Log pesan pelanggan di sistem CRM Anda untuk riwayat percakapan lengkap.
Analisis pola pesan masuk, waktu puncak, dan sentimen pelanggan.
Tangkap dan kualifikasi lead dari pertanyaan pelanggan yang masuk.
Download dan simpan gambar atau dokumen yang dikirim pelanggan.

Praktik Terbaik

Ikuti praktik ini saat menangani event channel.message_in.
  1. Validasi Struktur Payload
    if (!event || !message || !message.content) {
      console.error('Struktur payload tidak valid');
      return res.status(400).send('Invalid payload');
    }
    
  2. Deduplikasi Event
    const processedEvents = new Set();
    const eventId = `${event}_${message.id}`;
    
    if (processedEvents.has(eventId)) {
      return res.status(200).send('OK');
    }
    
    processedEvents.add(eventId);
    
  3. Tangani Berbagai Tipe Konten
    if (content.type === 'text') {
      // Tangani teks
    } else if (content.attachments) {
      // Tangani media
    } else {
      console.warn('Tipe konten tidak dikenal:', content.type);
    }
    
  4. Simpan Konteks Percakapan
    // Lacak state percakapan
    const conversationState = {
      id: conversation_id,
      label: conversation_label,
      needsHuman: need_human === 1
    };
    
    await db.conversations.upsert(conversationState);
    

Penanganan Error

app.post('/webhook', async (req, res) => {
  try {
    const { event, message } = req.body;
    
    if (event === 'channel.message_in') {
      // Proses pesan
      await handleIncomingMessage(message);
    }
    
    res.status(200).send('OK');
  } catch (error) {
    console.error('Error memproses channel.message_in:', error);
    // Tetap kembalikan 200 untuk menghindari retry pada error pemrosesan
    res.status(200).send('OK');
  }
});
Kembalikan 200 OK meskipun Anda mengalami error pemrosesan, kecuali Anda ingin CSKU AI me-retry webhook.

Event Terkait