Redis Pub/Sub
Redis Pub/Sub
OmniStream memakai Redis tidak sebagai cache, melainkan sebagai
message bus realtime. Event yang harus sampai ke browser user
dipublikasikan di channel pub/sub Redis; ws-server subscribe ke
keempat channel dan me-routing-kan ke WebSocket klien yang relevan.
Ada empat channel aktif:
conversation_updatestyping_indicatorsagent_presencesla_breaches
Semua channel bersumber pada konvensi redis::cmd("PUBLISH") dari
service publisher, dan ws-server men-subscribe-nya di
crates/ws-server/src/subscriber.rs:16-44:
Code
Channel conversation_updates
Publisher: chat-engine (setiap channel), api-gateway
(untuk event user-action seperti assign/transfer/resolve).
Subscriber: ws-server.
Payload schema: ConversationUpdateEvent di
crates/omni-common/src/models/events.rs:64:
Code
MessagePreview sebagai opsional sub-struct membawa cukup data
untuk preview di Inbox tanpa me-load pesan penuh:
Code
Routing di ws-server: Event NewMessage dan
StatusChanged dikirim ke agent yang ditugaskan (assigned_agent_id)
plus semua supervisor/admin yang sedang online. Event
AgentAssigned dan Transferred dikirim ke agent lama dan baru
sekaligus supaya kedua sisi UI refresh.
Kenapa ada juga di webhook dispatcher: api-gateway lewat
webhook_dispatcher juga subscribe ke channel yang sama untuk
memicu outgoing webhook ke endpoint customer — lihat
developer/webhook/outgoing.
Channel typing_indicators
Publisher: ws-server (diterima dari client message WebSocket,
lihat developer/websocket/client-messages).
Subscriber: ws-server (broadcast ke semua koneksi).
Payload schema: JSON sederhana, tidak ada struct formal —
event diteruskan apa adanya oleh broadcast handler
(crates/ws-server/src/subscriber.rs:98-106):
Code
Frontend mem-filter berdasar conversation_id dan menyembunyikan
event dari sender itu sendiri (supaya user tidak melihat indikator
ketik milik dirinya sendiri).
Typing indicator adalah satu-satunya channel yang di-broadcast ke semua koneksi WebSocket. Volume-nya rendah (setiap agent hanya me-ngetik saat sedang aktif) jadi overhead broadcast-nya marginal. Kalau di masa depan jumlah agent simultan naik signifikan, ini jadi kandidat pertama untuk re-design ke channel per-conversation.
Channel agent_presence
Publisher: ws-server (saat WebSocket connection open/close).
Subscriber: ws-server (broadcast ke semua agent).
Payload schema: AgentPresenceEvent di
crates/omni-common/src/models/events.rs:105:
Code
Frontend memakai event ini untuk menampilkan dot hijau/abu-abu di daftar agent di halaman User Management dan di sidebar Inbox (saat memilih siapa yang akan menerima transfer).
Kenapa publish-nya di ws-server dan bukan api-gateway? Karena
kondisi "online/offline" otoritatifnya adalah apakah ada koneksi
WebSocket terbuka, bukan row database. Kalau dua tab browser
terbuka dan satu ditutup, ws-server masih menganggap agent
online sampai tab terakhir tertutup.
Channel sla_breaches
Publisher: api-gateway/src/scheduler.rs::publish_breach_event
(scheduler.rs:422-444).
Subscriber: ws-server — kirim ke assigned agent + semua
supervisor/admin (subscriber.rs:107 dst.).
Payload schema: SlaBreachEvent di
crates/omni-common/src/models/sla.rs (struct internal, tidak
di-expose di events.rs):
Code
Kapan dipublish: Scheduler polling di api-gateway berjalan
setiap 30 detik. Untuk setiap sla_policies aktif, ia me-load
semua open conversation yang match (prioritas match:
channel+division(4) > division(2) > channel(2) > default(1), logic
di scheduler.rs::find_policy), lalu mengecek apakah deadline
first_response atau resolution sudah lewat tanpa entri di
sla_breach_logs. Breach baru → insert ke sla_breach_logs + publish.
Detail halaman admin: panduan/admin/kebijakan-sla.
Detail implementasi scheduler: crates/api-gateway/src/scheduler.rs.
Cara menghubungkan ke browser
Browser tidak bicara dengan Redis secara langsung. Alur lengkap:
Code
Detail koneksi WebSocket dari sisi client ada di
developer/websocket/koneksi dan
bentuk event yang diterima browser ada di
developer/websocket/events.
Konfigurasi dan debugging
Variabel lingkungan:
REDIS_URL— wajib (mis.redis://redis:6379). Dipakai oleh publisher maupun subscriber. Tidak ada default.
Debug cepat dari VPS:
Code
Kalau NUMSUB menunjukkan 0 untuk salah satu channel, artinya
ws-server tidak tersambung — cek log ws-server untuk pesan
"Starting Redis subscriber for channels ..." yang seharusnya
muncul saat boot.
Referensi
- Skema event:
crates/omni-common/src/models/events.rs - Publisher:
crates/chat-engine/,crates/api-gateway/src/scheduler.rs,crates/api-gateway/src/webhook_dispatcher.rs - Subscriber:
crates/ws-server/src/subscriber.rs:16-124 - WebSocket routing:
crates/ws-server/src/handler.rs