Hydration mismatch terjadi ketika markup yang dirender di server tidak sama dengan DOM yang dirender ulang oleh client. Saat memanfaatkan konten OCR dinamis, seperti teks hasil pemindaian kode via pipeline OCR (misalnya pendekatan pxpipe), perbedaan kecil dalam struktur HTML atau data dapat menyebabkan UI ‘lompat’ atau muncul error konsol. Artikel ini langsung membahas debug hydration mismatch dari konten OCR dinamis di SSR, mulai dari pengambilan data hingga strategi mitigasi UX.

Pipeline OCR hingga Hydration

Validasi pipeline dimulai sejak fetch data OCR. Ketika SSR merender halaman, pastikan semua data yang akan dimasukkan ke dalam markup tersedia sebelum rendering server dimulai. Biasanya alur sederhana:

  1. Fetch gambar kode.
  2. Operasikan OCR di backend atau service terpisah (pastikan latency di bawah time budget SSR).
  3. Normalisasi dan validasi hasil OCR.
  4. Serialisasi data ke dalam props/initial state yang akan dicetak di HTML server.
  5. Client melakukan hydration dengan state yang sama.

Jika ada probabilitas OCR menghasilkan teks berbeda tiap request (misalnya noise atau karakter yang hilang), pastikan hasil server tetap deterministik sebelum dikirim ke client. Salah satu pendekatan adalah menyimpan snapshot data yang sudah tervalidasi, sehingga markup awal selalu konsisten.

Validasi Data dan Serialisasi State

Persamaan DOM bergantung pada kesamaan data. Perbedaan kecil seperti tanggal atau nilai default dapat membuat struktur DOM berubah. Strategi yang efektif meliputi:

  • Schema validation untuk setiap hasil OCR (misalnya menggunakan JSON Schema atau zod) agar komponen selalu menerima jenis dan format yang sama.
  • Normalisasi teks (pangkas whitespace, gunakan casing konsisten) sebelum rendering.
  • State serialization eksplisit di HTML agar client dan server menggunakan payload identik.

Contoh serialization sederhana:

const ocrResult = normalizeOcr(rawData);
const html = `
  
${renderOcrMarkup(ocrResult)}
`;

Client kemudian membaca data-state tersebut untuk hydrasi:

const root = document.getElementById('ocr-root');
const preloadedState = JSON.parse(root.getAttribute('data-state'));
hydrateRoot(preloadedState);

Dengan pendekatan ini, markup server dan data client selalu sinkron.

Menangani Perbedaan DOM dan Hydration Mismatch

Debug hydration mismatch memerlukan inspeksi DOM server vs client:

  • Periksa console browser untuk pesan mismatch (sering muncul di React/Next.js).
  • Bandingkan node tree pada tab Elements setelah initial load dan setelah client hydration. Cari atribut dinamis atau teks yang berubah.
  • Perhatikan nilai default di atribut form (checked, selected, value) karena React kadang memaksa controlled state.

Salah satu kesalahan umum: server merender teks placeholder sementara client mengganti hasil OCR setelah fetching tambahan. Solusi:

  • Gunakan fallback sementara yang identik di server dan client, misalnya teks “Memproses hasil scan…” yang juga akan ditimpa oleh hasil OCR ketika siap.
  • Tunda rendering komponen yang bergantung data asynchronous hingga data tersedia (gunakan suspense atau conditional rendering) sehingga tidak ada markup berbeda.

Jika perilaku dinamis tak terhindarkan, pastikan perubahan tidak langsung memodifikasi struktur atas DOM yang sudah dirender: lakukan patching via client-only effect setelah hydration selesai.

Debugging dengan Developer Tools

Beberapa langkah developer tools membantu memperjelas mismatch:

  • Gunakan tab Performance untuk melihat apakah hydration menyebabkan repaint besar atau layout shift.
  • Aktifkan Highlight updates (React DevTools) untuk mengetahui apakah komponen melakukan re-render berulang karena data yang berubah.
  • Gunakan breakpoint pada kode yang men-trigger OCR hasil parsing agar bisa melihat state awal vs update.

Untuk DOM comparison manual, ekspor snapshot markup server (misalnya via server log) lalu bandingkan dengan markup client (view source atau Elements). Jika struktur berbeda, cari elemen yang hilang/tambahan.

Testing Lintas Environment

Hydration mismatch sering muncul di environment tertentu (mode production vs development). Beberapa tips testing:

  • Testing server render dengan build production untuk memastikan markup final sesuai.
  • Simulasi network variabilitas (slow 3G/CPU throttling) agar perbedaan timing fetch OCR terlihat.
  • Integrasi lintas browser karena behavior hydration bisa berbeda antara Chromium dan WebKit.

Cek log server untuk memastikan data OCR yang sama dikirim ke template dan tidak ada fallback berbeda disisipkan karena error fetch di server.

Mitigasi UX Membingungkan

Kebingungan UX timbul ketika user melihat konten berubah drastis setelah hydration. Strategi yang bisa diterapkan:

  • Gunakan skeleton atau placeholder statis yang identik server dan client agar perubahan terprediksi.
  • Transition halus untuk konten yang harus di-update (misalnya fade-in), dengan persyaratan bahwa struktur DOM tidak berubah.
  • Berikan indikator status (spinner, label “Memuat hasil OCR”) yang juga di-render di server, sehingga user tahu perubahan dini normal.

Dengan pendekatan ini, hydration mismatch tidak hanya dicegah secara teknis, tetapi pengalaman pengguna tetap koheren.