Menghadapi sistem monolitik warisan (legacy monolith) yang minim dokumentasi dan tanpa cakupan unit test yang memadai adalah tantangan klasik rekayasa perangkat lunak. Ketika skala trafik meningkat dan kebutuhan fitur baru terhambat oleh tight coupling, tim engineering dihadapkan pada dilema: merombak total dari nol (big-bang rewrite) atau memotong fungsionalitas secara inkremental menggunakan Strangler Fig Pattern.

1. Trade-off Arsitektur: Strangler Fig vs Rewrite Total

Pilihan modernisasi bukan sekadar preferensi teknis, melainkan manajemen risiko operasional dan efisiensi alokasi sumber daya rekayasa.

Big-Bang Rewrite

Rewrite total bertujuan membangun kembali seluruh kapabilitas sistem lama menggunakan stack dan paradigma arsitektur baru dari titik awal.

  • Risiko Regresi & Blast Radius: Sangat tinggi. Monolit warisan sering menyimpan logika bisnis implisit (edge cases, bug-turned-feature, dan perbaikan darurat tak terdokumentasi). Menulis ulang sistem secara penuh hampir selalu melewatkan perilaku-perilaku non-standar ini hingga sistem diuji langsung oleh beban produksi.
  • Dual-running Operational Cost: Rendah di awal karena tim hanya memelihara sistem lama sambil fokus membangun sistem baru. Namun, biaya melonjak drastis saat fase cutover akibat perbedaan skema data dan durasi downtime migrasi massal.
  • Maintainability & Delivery Velocity: Selama proses penulisan ulang (yang kerap memakan waktu bulanan hingga tahunan), pengembangan fitur bisnis terhenti (feature freeze) atau tim harus melakukan implementasi ganda (fitur baru ditulis di sistem lama sekaligus sistem baru).

Strangler Fig Pattern

Pola Strangler Fig mengekstrak fungsi monolit lapis demi lapis ke dalam layanan baru (biasanya microservices atau monolit modular) di balik routing layer transparan hingga sistem lama perlahan usang dan dapat dipensiunkan.

  • Isolasi Boundary Domain: Domain dipisahkan secara bertahap menggunakan batas konteks (bounded context) yang terukur. Kegagalan ekstraksi hanya berdampak pada satu domain layanan, bukan keseluruhan platform.
  • Risiko Regresi: Rendah. Setiap domain yang dipindahkan dapat divalidasi perilakunya secara terisolasi sebelum migrasi domain berikutnya.
  • Dual-running Operational Cost: Tinggi secara teknis. Sistem monolit dan arsitektur baru berjalan bersamaan dalam periode transisi yang panjang. Diperlukan sinkronisasi data dua arah, manajemen transaksi terdistribusi, dan konsistensi data eventual.
  • Maintainability Tim: Beban kognitif terbagi antara memahami sistem lama dan merancang sistem baru, tetapi tim dapat merilis perubahan ke produksi secara kontinu tanpa menahan rilis fitur bisnis.

2. Metodologi Dekomposisi Bertahap

Mengurangi risiko regresi pada monolit tanpa test suite lengkap membutuhkan tiga pilar teknis: routing intermediasi, replikasi data berbasis event, dan verifikasi paritas melalui shadowing.

A. Routing Layer (Reverse Proxy / API Gateway)

Klien (web, mobile, atau 3rd party API) tidak boleh berinteraksi langsung dengan sistem baru atau sistem lama secara spesifik. Reverse proxy ditempatkan di depan kedua sistem sebagai facade. Proksi ini mengalihkan lalu lintas secara kondisional berdasarkan path, header, atau persentase beban ke layanan yang sesuai.

B. Sinkronisasi Data Tanpa Dual-Write (Change Data Capture)

Pola anti-pattern yang sering terjadi saat modernisasi adalah dual-write dari level aplikasi (menulis ke database lama dan database baru sekaligus dalam satu request handler). Pendekatan ini rentan terhadap split-brain bila terjadi kegagalan parsial jaringan atau database.

Pendekatan yang benar adalah memanfaatkan Change Data Capture (CDC) menggunakan tool seperti Debezium yang membaca transaction log database monolit (seperti MySQL Binlog atau PostgreSQL WAL), lalu mengirimkan mutasi data tersebut ke message broker (Kafka, RabbitMQ). Konsumen di sisi layanan baru memproses stream tersebut untuk memperbarui datastore lokal secara asinkron tanpa membebani performa database monolit.

C. Traffic Shadowing untuk Paritas Perilaku

Ketika unit test monolit tidak ada, verifikasi perilaku dilakukan menggunakan lalu lintas produksi riil melalui traffic shadowing (dark launching). Request yang masuk ke reverse proxy digandakan (mirrored): satu diteruskan ke monolit sebagai sumber kebenaran (respons dikirim ke klien), dan salinan request dikirim ke layanan baru (respons dibuang atau dialirkan ke sistem pembanding).

Dengan membandingkan respons dari monolit dan layanan baru secara asinkron (misalnya menggunakan tool pembanding diff seperti Diffy), tim dapat menemukan ketidakcocokan logika bisnis dan penanganan status kode sebelum proses cutover aktual dilakukan.

3. Implementasi Konfigurasi Reverse Proxy Transisi

Berikut adalah konfigurasi minimal NGINX yang mendemonstrasikan dua strategi Strangler Fig:

  1. Traffic Shadowing (Dark Launching): Menduplikasi request modul tertentu ke service baru untuk pengujian paritas tanpa memengaruhi pengguna.
  2. Inkremental Routing: Mengalihkan trafik modul yang telah teruji sepenuhnya ke service baru, sementara modul lain tetap berada di monolit.
upstream legacy_monolith {
    server 10.0.1.10:8080 max_fails=3 fail_timeout=10s;
    keepalive 32;
}

upstream new_order_service {
    server 10.0.2.20:3000 max_fails=3 fail_timeout=10s;
    keepalive 32;
}

upstream shadow_order_service {
    server 10.0.2.21:3000;
}

server {
    listen 80;
    server_name api.example.internal;

    # 1. Default routing: arahkan seluruh trafik yang belum termigrasi ke monolit
    location / {
        proxy_pass http://legacy_monolith;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
        proxy_http_version 1.1;
        proxy_set_header Connection "";
    }

    # 2. Tahap Uji Paritas: Mirror request /api/v1/orders ke service baru
    # Response dari shadow service akan diabaikan oleh NGINX
    location /api/v1/orders {
        mirror /mirror_order;
        mirror_request_body on;

        proxy_pass http://legacy_monolith;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_http_version 1.1;
        proxy_set_header Connection "";
    }

    location = /mirror_order {
        internal;
        proxy_pass http://shadow_order_service$request_uri;
        proxy_set_header Host $host;
        proxy_set_header X-Shadow-Traffic "true";
        proxy_http_version 1.1;
        proxy_set_header Connection "";
    }

    # 3. Tahap Cutover: Reroute permanen modul yang sudah teruji valid
    location /api/v1/payments {
        proxy_pass http://new_order_service;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
        proxy_http_version 1.1;
        proxy_set_header Connection "";
    }
}

4. Matriks Evaluasi Keputusan

Gunakan matriks berikut untuk menentukan pendekatan arsitektural yang sesuai dengan kondisi teknis dan batasan organisasi:

Kriteria EvaluasiStrangler Fig PatternRewrite Total (Big-Bang)
Pemahaman Domain & DokumentasiMinim/Sebagian. Pengetahuan digali bertahap per modul melalui traffic inspection.Tinggi. Semua aturan bisnis harus dipahami sebelum implementasi dimulai.
Kopling Kode (Coupling)Tinggi. Sistem monolitik memiliki keterikatan database atau dependensi internal yang rumit.Rendah atau Monolit Berukuran Kecil (di bawah ~20k LOC) dengan dependensi sederhana.
Teknologi Dasar (Runtime/Stack)Masih didukung infrastruktur modern (misal: Java 8+, PHP 7+, Node LTS) yang bisa dipadukan.Usang total (misal: proprietary language mati, runtime tanpa dukungan arsitektur cloud/kontainer).
Toleransi Downtime BisnisNol (Zero-downtime cutover bertahap).Toleran terhadap jendela maintenance/downtime saat migrasi data massal.
Kapasitas Operasional DevOpsHarus matang: butuh keahlian CDC, distributed tracing, gateway proxy, dan observabilitas.Cukup standar selama fase build; beban terkonsentrasi saat fase cutover final.
Time-to-ValueCepat: modul pertama dapat masuk produksi dalam hitungan minggu.Lambat: nilai bisnis baru terlihat setelah keseluruhan sistem siap dideploy.

Kesimpulan dan Rekomendasi Praktis

Modernisasi monolit warisan bukan keputusan biner antara mengikuti tren arsitektur terkini atau mempertahankan sistem usang. Jika monolit menangani operasi inti bisnis dengan dependensi data yang kompleks, Strangler Fig Pattern adalah strategi teraman untuk memitigasi risiko kegagalan sistemik.

Pilihlah Big-Bang Rewrite hanya jika ukuran basis kode relatif kecil, logika domain telah terdokumentasi dengan presisi absolut, atau tech stack dasar telah sepenuhnya deprecated sehingga tidak memungkinkan integrasi routing transisi.