D
Engineering

Database

MongoDB sebagai datastore via Mongoose 9.1. DB dazo lokal atau remote. connectDB fail-fast via process.exit 1 tapi tidak di-await di app.ts. Primary key field id string UUID. Empat koleksi — devices, admin_devices, chat_inbox, chat_histories.

engine-whatsapp memakai MongoDB sebagai datastore via Mongoose 9.1. Tidak ada migration — bentuk dokumen diturunkan dari Mongoose schema di src/model/.

Koneksi MongoDB

src/config/database.ts — connectDB() async, memakai MONGO_URL dari .env:

ts
const MONGO_URL = config.mongo_url;   // dari .env

export const connectDB = async (): Promise<void> => {
  try {
    await mongoose.connect(MONGO_URL);
    console.log("Mongodb Connected");
  } catch (error: any) {
    console.error("Mongodb Error Connection: ", error)
    process.exit(1);   // fail-fast
  }
}
EnvironmentDatabaseHost
lokal (default)dazo127.0.0.1:27017
remotedari MONGO_URLconnection string dari tim

Primary key

Sama seperti dazoapp, backend-go, dan engine-bot, koleksi Dazo memakai field id (string UUID) sebagai primary key logis — bukan _id Mongo default:

ts
const device = await DeviceModel.findOne({ id: instanceId });

_id Mongo tetap ada (auto ObjectId), tapi query bisnis berdasarkan id string.

Pola akses koleksi

Engine WhatsApp memakai Mongoose model — ada layer ODM tipis:

ts
// src/model/devices.model.ts
const DeviceSchema = new Schema<DeviceCollection>({ id: { type: String, required: true, index: true }, ... });
export const DeviceModel = model<DeviceCollection>('devices', DeviceSchema, 'devices');

// src/service/devices/deviceServices.ts
const device = await DeviceModel.findOne({ id: instanceId });

Koleksi utama

Hanya 4 koleksi yang dikelola engine-whatsapp:

KoleksiModelDipakai untuk
devicessrc/model/devices.model.tsDevice milik user. Diupdate saat koneksi open/close (no_wa, is_connected)
admin_devicessrc/model/admin_devices.model.tsFallback bila instanceId tidak ada di devices; punya field tambahan status (0/1)
chat_inboxsrc/model/chatInbox.model.tsPesan. Dibaca engine untuk mencari temp_id. strict: false
chat_historiessrc/model/chatHistory.model.tsSesi percakapan per nomor. Dibuat otomatis saat ada pesan masuk bila belum ada yang aktif

devices vs admin_devices

Saat status koneksi berubah (open/close), engine mencari devices lebih dulu. Jika tidak ketemu, update diarahkan ke admin_devices:

ts
// src/service/whatsappService.ts — connection.update handler
let deviceMember = await DeviceService.findOne(instanceId);

if (!deviceMember) {
  // Fallback ke admin_devices
  await DeviceService.updateDeviceAdmin(instanceId, {
    no_wa: phoneNumber,
    is_connected: 'Connected',
    status: 1,
  });
} else {
  await DeviceService.update(instanceId, {
    no_wa: phoneNumber,
    is_connected: 'Connected',
  });
}

Pertahankan pola percabangan ini saat menyentuh kode update device.

admin_devices punya field ekstra status: 0|1 (0 = disconnected, 1 = connected) yang tidak ada di devices.

Relasi custom

Relasi implicit via instanceId — bukan _id Mongo:

  • devices.id / admin_devices.id = instanceId = nama folder session/auth/<instanceId>
  • chat_inbox.instance = instanceId
  • chat_histories.instance = instanceId

Shared dengan dazoapp dan backend-go

KoleksiEngine WhatsApp menulisEngine WhatsApp membacaDibagi dengan
devices✅ update no_wa, is_connected✅ findOne untuk chat_histories lookupdazoapp, backend-go
admin_devices✅ update (fallback)❌dazoapp
chat_inbox❌ read-only✅ cari temp_idbackend-go (writer)
chat_histories✅ create✅ cari existingbackend-go

chat_histories logic

ChatHistoryService.manageChatHistory() (src/service/chatHistory/chatHistoryService.ts) dipanggil untuk setiap pesan masuk:

  1. Cari devices berdasarkan instanceId untuk dapat store_id
  2. Jika device tidak ada → return (tidak buat history)
  3. Cari chat_histories dengan filter: store_id + instance + nohp + end_date: null + status != "close"
  4. Jika tidak ada → buat baru dengan id: uuid, status: "open", chat_status: "new", chat_start: messageId
  5. Jika ada → skip (tidak duplikat)

Nomor disimpan dengan format +628... (prefix + lalu nomor tanpa @s.whatsapp.net).

Inkonsistensi yang diketahui

MasalahDetail
Nama model Admin_DeviceMongoose auto-pluralize → koleksi admin_devices (bukan Admin_Devices)
connectDB tidak di-awaitapp.ts:37 — server.listen jalan berbarengan dengan DB connect
chat_inbox.strict: falseField tambahan dari writer (backend-go) tetap tersimpan tanpa validasi
Tidak ada index kompositQuery chat_histories filter store_id + instance + nohp + end_date + status tanpa compound index

Lihat Tech Debt untuk daftar lengkap.

Konteks vs dazoapp, backend-go, engine-bot

Aspekdazoapp (Laravel)backend-goengine-botengine-whatsapp
ODM/ORMMongoDB Eloquentmongo-driverMongooseMongoose
Jumlah koleksi dikelola79 model~5244
Multi-DB4 koneksi2 koneksi11
PKUUID stringfield idfield idfield id
Tenant scopestore_idstore_idstore_idinstanceId (per device)
Startup fail-fast✅❌❌✅ (tapi tidak di-await)
AuthJWT issuer—validate-only❌ tidak ada

Langkah berikutnya