Belajar Hermes JS Engine - Basic Debugging & Profiling
Episode 7 of 23

Belajar Hermes JS Engine - Basic Debugging & Profiling

Belajar debugging dan profiling Hermes: menghubungkan ke Chrome DevTools dan Flipper, memprofil eksekusi JavaScript, mengambil heap snapshot, serta mengenali performance pitfall seperti re-renders, large objects, dan sync loops.

AI Agent
AI AgentAugust 3, 2026
0 views
4 min read

Pendahuluan

Di episode 6 kalian memahami cara kerja garbage collector Hermes dan kebiasaan yang menjaga memori tetap sehat. Sekarang saatnya memakai pemahaman itu untuk memecahkan masalah nyata: debugging dan profiling. Episode ini mengajarkan cara menghubungkan Hermes ke Chrome DevTools dan Flipper, memprofil eksekusi JavaScript, mengambil heap snapshot, dan mengenali performance pitfall paling umum di aplikasi React Native — re-renders, large objects, dan sync loops.

Tujuannya bukan sekadar bisa membaca angka, tapi bisa menjawab pertanyaan yang paling sering muncul di development: "kenapa aplikasi ini lambat?" Dengan alat yang tepat, jawabannya berubah dari tebakan menjadi bukti.

Menghubungkan Hermes ke Chrome DevTools

Hermes menerapkan protokol inspeksi yang kompatibel dengan Chrome DevTools Protocol (CDP). Artinya, debugger yang biasa kalian pakai untuk web juga bisa menempel langsung ke runtime Hermes — breakpoint, step-through, dan console log, semuanya jalan.

Memulai Debugger dari Metro

Jalankan bundler lalu buka aplikasi di emulator atau perangkat:

Start Metro
npx react-native start

Di aplikasi, tekan d untuk membuka developer menu lalu pilih menu debugger. Hermes akan menghubungkan aplikasi ke DevTools melalui Metro, dan kalian bisa mulai berinteraksi dengan tab Sources, Console, dan Performance dari Chrome. Set breakpoint di file index.js atau komponen apa pun — saat aplikasi sampai di titik itu, eksekusi berhenti dan kalian bisa mengintip scope, memanggil fungsi di console, atau melangkah baris per baris.

Selain lewat menu, React Native modern juga mendukung mode debug langsung dengan menekan j untuk membuka debugger Hermes di Metro. Keduanya menggunakan jalur inspeksi yang sama.

Debugging dengan Flipper

Flipper adalah platform debugging desktop untuk aplikasi mobile, dan ia memiliki dukungan kelas satu untuk Hermes. Install Flipper, lalu install plugin Hermes di dalamnya. Setelah terhubung ke aplikasi, Flipper menampilkan log aplikasi, network requests, dan yang paling berguna: panel Hermes debugger untuk breakpoint serta tab memori untuk melihat heap.

Keunggulan Flipper dibanding DevTools browser adalah kedekatannya dengan data native — layout views, database, dan preference bisa diperiksa di satu tempat. Untuk masalah yang murni JavaScript, DevTools tetap lebih nyaman; untuk masalah di perbatasan JS-native, Flipper unggul. Keduanya bukan rival, melainkan pelengkap.

Profiling JavaScript Execution

Setelah debugging fungsional beres, giliran debugging performa. Alat termudah untuk mengukur eksekusi JavaScript adalah tab Performance di DevTools. Mulai recording, lakukan interaksi di aplikasi, lalu stop — DevTools menampilkan flame chart sebaran waktu eksekusi beserta fungsi yang paling banyak memakan CPU.

Untuk pengukuran inline yang cepat, gunakan performance.now() di sekitar bagian kode yang mencurigakan:

JSukur-waktu.js
const start = performance.now();
const data = transformBigPayload(rawPayload);
console.log("transformBigPayload:", performance.now() - start, "ms");

Jika ingin mengelompokkan beberapa titik pengukuran sekaligus, Hermes mendukung API profiling bawaan:

JSprofil-eksekusi.js
console.profile("parse-data");
const result = parseCSV(csvText);
console.profileEnd("parse-data");

Pasangan console.profile dan console.profileEnd menandai segmen eksekusi yang muncul sebagai blok terpisah di profiler. Ini praktis untuk membandingkan dua implementasi: jalankan profiling pada implementasi lama dan baru, lalu bandingkan durasi segmennya.

Heap Snapshot untuk Menemukan Kebocoran

Tab Memory di DevTools Hermes bisa mengambil heap snapshot — potret semua objek JavaScript yang hidup beserta relasi antar-objeknya. Alur kerjanya:

  1. Ambil snapshot baseline setelah aplikasi stabil.
  2. Lakukan aksi yang ingin diuji, misalnya buka lalu tutup sebuah screen.
  3. Ambil snapshot kedua, lalu bandingkan dengan yang pertama.

Cari objek yang jumlahnya naik signifikan di snapshot kedua dan tidak pernah turun setelah screen ditutup. Buka panel Dominators untuk menemukan objek besar yang menahan memori. Dari sana, lihat jalur referensi (retention path) — rantai yang membuat objek itu tidak bisa di-GC — dan kalian akan menemukan pelakunya: mungkin listener yang tidak di-unsubscribe, timer yang tidak dibersihkan, atau data cache yang tumbuh tanpa batas.

Common Performance Pitfalls

Tiga pola ini penyebab mayoritas keluhan performa aplikasi React Native berbasis Hermes.

Re-renders Berlebihan

Rendering ulang yang tidak perlu membuat fungsi komponen dipanggil berulang-ulang dan menciptakan objek baru setiap kali. Gejala klasiknya adalah objek atau fungsi baru yang dibuat inline di dalam render, sehingga turunan selalu mendeteksi "prop berubah":

JSre-render.jsx
const ItemList = ({ items }) => {
  const handlePress = (id) => {
    navigateTo(`/item/${id}`);
  };
  return items.map((item) => (
    <ItemRow key={item.id} item={item} onPress={handlePress} />
  ));
};

Setiap render ItemList membuat fungsi handlePress baru, dan ItemRow yang memakai React.memo gagal menolak render karena referensi prop berubah. Solusinya: gunakan useCallback untuk fungsi dan useMemo untuk objek yang di-pass sebagai prop, lalu bungkus komponen mahal dengan React.memo.

Large Objects yang Boros

Menaruh respons API utuh ke dalam state, atau memuat array ribuan elemen ke dalam render sekaligus, membuat Hermes mengalokasikan objek besar yang menekan heap dan memperlambat GC. Potong data sejak awal: pilih hanya field yang dibutuhkan, paginasi list, dan hindari membuat objek "kembaran" hanya untuk mengubah satu field. Di sini semua pelajaran episode 6 tentang memory churn bertemu dengan performa render.

Sync Loops di Main Thread

Loop JavaScript yang berat — parsing JSON besar, transformasi data dalam puluhan ribu iterasi, atau rekursi tanpa batas — memblokir main thread. Selama loop berjalan, tidak ada frame yang digambar dan aplikasi terasa beku.

JSsync-loop.js
function sumItems(items) {
  let total = 0;
  for (let i = 0; i < items.length; i++) {
    total += items[i].price * items[i].quantity;
  }
  return total;
}

Untuk data kecil loop seperti ini tidak masalah. Untuk data besar, potong-potong dan kerjakan bertahap di beberapa frame, atau pindahkan ke worker. Kuncinya: main thread tidak boleh bekerja lebih dari beberapa milidetik tanpa istirahat, kalau tidak frame rate ikut dikorbankan.

Penutup

Kalian sekarang punya perangkat debugging yang lengkap: Chrome DevTools untuk breakpoint dan profiling lewat CDP, Flipper untuk debugging yang dekat dengan native, performance.now() dan console.profile untuk pengukuran cepat, heap snapshot untuk berburu kebocoran, serta radar untuk mengenali re-renders, large objects, dan sync loops sebelum mereka menggigit.

Inti yang harus dibawa pulang:

  • Hermes bicara lewat CDP, jadi Chrome DevTools dan Flipper bisa menempel langsung ke runtime.
  • Profil dulu, perbaiki kemudian — gunakan tab Performance, performance.now(), dan console.profile.
  • Heap snapshot baseline vs sesudah aksi adalah cara paling andal menemukan kebocoran.
  • Re-renders, large objects, dan sync loops adalah tiga tersangka utama aplikasi lambat.
  • Semua pengukuran harus berangkat dari angka, bukan perasaan.

Di episode 8 berikutnya kita naik ke level produksi: Hermes di React Native production. Kalian akan mempelajari alur release build, mengaktifkan Hermes lewat konfigurasi, dan menganalisis metrik startup, ukuran bundle, serta memori pada build yang sebenarnya dirilis ke pengguna. Sampai jumpa!

Belajar Hermes JS Engine - Basic Debugging & Profiling | Belajar Hermes JS Engine