Keputusan arsitektur yang terasa final ternyata punya asumsi bisnis di baliknya. Begitu asumsinya berubah, keputusannya layak ikut ditinjau ulang.
Ada satu catatan dari sesi perencanaan sistem transaksi pertama yang pernah kami rencanakan. Bunyinya singkat: "Multi-tenant tidak perlu."
Keputusan itu dikunci. Dan waktu itu, ia masuk akal sepenuhnya.
Beberapa bulan kemudian, sebelum satu baris kode ditulis, keputusan itu kami buka lagi.
Keputusan sebagai Konsekuensi dari Premis
Model bisnis kami waktu itu jelas: membangun demo untuk pitching, kalau deal dituning sesuai kebutuhan client, lalu dideploy. Satu project untuk satu client.
Dalam model itu, arsitektur single-tenant adalah konsekuensi langsung dari premisnya. Satu deployment per client, tiap instance berdiri sendiri. Bersih, terkontrol, sesuai dengan cara kerja yang ada.
Kami tahu ada pola lain. Referensi kami sebelumnya sudah pakai pola multi-tenant. Tapi untuk konteks ini, kami sadar memilih single-tenant. Keputusannya dikunci.
Asumsi yang Bergeser
Yang mengubahnya adalah pemahaman tentang untuk siapa produk ini dibangun.
Dari satu obrolan ke obrolan berikutnya dengan pemilik usaha, mulai dari teman yang punya brand fashion sampai beberapa pemilik vapestore, pola masalah yang sama terus muncul dari orang yang berbeda. Operasional yang tersebar, data yang tidak terhubung, akuntabilitas yang hilang di antara shift dan cabang.
Perlahan, yang kami rencanakan bukan lagi sesuatu untuk satu client yang datang, tapi sesuatu yang menjawab pola masalah yang lebih luas. Skalanya berbeda.
Keputusan yang Ikut Berubah
Begitu asumsinya berubah, keputusan yang tadinya dikunci jadi pertanyaan terbuka lagi.
Model per-client di skala ini berarti tiap user baru adalah deployment baru, maintenance yang tumbuh linear. Premis di balik keputusan itu sudah berbeda, dan keputusannya harus ikut ditinjau.
Merlin akhirnya dibangun dengan arsitektur multi-tenant sejak migration pertama. Keputusannya berubah sebelum kode pertama ditulis.
Konsekuensi yang Ikut Dibangun
Shared-database multi-tenant artinya isolasi antar toko sepenuhnya jadi tanggung jawab di level kode. Beberapa bulan setelah Merlin live, kami menemukan bug di rate limiter: semua tenant berbagi satu bucket yang sama karena traffic internal melewati jalur berbeda dari yang diperkirakan. Satu toko yang ramai bisa membuat toko-toko lain mendapat respons error.
Keputusan arsitektur terus hidup di dalam sistem yang dibangun di atasnya.
Keputusan sebagai Hipotesis
Keputusan awal yang kami kunci untuk salah satu project demo adalah hipotesis terbaik berdasarkan pemahaman yang kami punya saat itu: untuk satu client, model per-project, skala yang terbatas. Dalam konteks itu, keputusannya valid.
Yang berubah adalah pemahaman kami tentang untuk siapa produk ini dibangun, dan seberapa luas pola masalah yang ingin diselesaikan. Begitu pemahamannya berubah, keputusan yang terasa final punya ruang untuk ditinjau ulang.
Ia berubah karena pemahamannya terhadap produk berkembang — bukan karena teknologinya berubah.