Husky di Next.js paling sering dipakai untuk mencegah masalah masuk ke repository terlalu cepat. Alih-alih menunggu error muncul di CI atau saat code review, Husky menjalankan hook Git seperti pre-commit dan pre-push agar lint, format, test, atau type check bisa dijalankan otomatis sebelum perubahan benar-benar dikirim.

Untuk proyek Next.js, pendekatan ini sangat berguna karena alur kerjanya biasanya melibatkan banyak file frontend, API route, konfigurasi environment, dan integrasi tooling seperti ESLint, Prettier, TypeScript, serta test runner. Dengan konfigurasi yang tepat, Husky membantu menjaga kualitas kode tanpa memperlambat developer secara berlebihan.

Apa itu Husky dan kenapa relevan untuk Next.js?

Husky adalah alat untuk mengelola Git hooks di proyek JavaScript/TypeScript. Git hooks sendiri adalah skrip yang dijalankan pada momen tertentu, misalnya sebelum commit, sebelum push, atau setelah merge.

Di proyek Next.js, Husky relevan karena banyak masalah umum sebenarnya bisa dicegah sangat awal, misalnya:

  • File lolos commit padahal melanggar aturan ESLint.

  • Kode tidak rapi karena format tidak konsisten.

  • TypeScript error baru ketahuan saat build.

  • Test dasar gagal tetapi perubahan tetap dipush.

  • File .env atau data rahasia tidak sengaja ikut ter-commit.

Intinya, Husky bukan pengganti CI/CD, tetapi lapisan validasi pertama di mesin developer.

Kasus penggunaan Husky di Next.js yang paling bermanfaat

1. Menjalankan lint sebelum commit

Ini adalah penggunaan paling umum dan paling masuk akal. Next.js umumnya sudah terintegrasi baik dengan ESLint, sehingga hook pre-commit bisa dipakai untuk memastikan file yang akan di-commit tidak membawa masalah gaya penulisan atau pola kode yang dilarang.

Manfaatnya:

  • Mengurangi noise saat code review.

  • Mencegah error sederhana masuk ke branch utama.

  • Menjaga konsistensi antar developer.

Praktik yang disarankan: jalankan lint hanya untuk file yang berubah, bukan seluruh proyek, agar commit tetap cepat.

2. Menjalankan formatter otomatis sebelum commit

Pada tim frontend, konflik style code sering membuang waktu. Dengan Husky, Anda bisa menjalankan formatter seperti Prettier sebelum commit. Hasilnya, indentasi, tanda kutip, trailing comma, dan format JSX tetap konsisten tanpa perlu diingat manual.

Ini sangat terasa manfaatnya pada proyek Next.js yang banyak berisi komponen React, file CSS, JSON, dan konfigurasi.

3. Menjalankan type check sebelum push

Jika proyek memakai TypeScript, error tipe sering tidak langsung terlihat hanya dari linting. Karena type check bisa lebih berat, banyak tim memilih menjalankannya di hook pre-push, bukan pre-commit. Dengan begitu, proses commit tetap ringan, tetapi developer tetap dicegah mendorong kode yang jelas rusak.

Ini cocok untuk kasus seperti:

  • Props komponen tidak sesuai tipe.

  • Return value API route tidak konsisten.

  • Import atau utility function berubah tetapi tidak memperbarui pemanggilnya.

4. Menjalankan test cepat sebelum push

Jika Anda punya unit test atau integration test yang relatif cepat, Husky bisa membantu menjalankannya sebelum push. Pendekatan ini berguna untuk mencegah branch remote terisi perubahan yang langsung gagal di CI.

Namun, jangan memaksa seluruh test suite berat di pre-commit. Untuk proyek Next.js yang punya banyak test UI atau integration test, hal itu bisa memperlambat workflow dan justru membuat developer ingin melewati hook.

5. Mencegah file sensitif ikut ter-commit

Kasus ini sering diremehkan, padahal penting. Di proyek Next.js, file seperti .env, .env.local, dump data, atau file kredensial sementara bisa saja tidak sengaja ikut staged. Husky dapat dipakai untuk memeriksa daftar file yang akan di-commit dan menggagalkan commit jika ada file terlarang.

Ini bukan pengganti pengelolaan secret yang benar, tetapi lapisan pencegahan yang sangat berguna.

6. Validasi pesan commit

Pada tim yang memakai standar seperti Conventional Commits, Husky dapat menjalankan hook commit-msg untuk memastikan format pesan commit konsisten. Ini bermanfaat jika pipeline rilis atau changelog bergantung pada format commit.

Contohnya:

  • feat: tambah halaman checkout

  • fix: perbaiki error hydration di navbar

Cara setup Husky di proyek Next.js

Berikut contoh setup yang umum dan aman untuk sebagian besar proyek Next.js. Contoh ini menggabungkan Husky dengan lint-staged agar hanya file yang berubah yang diperiksa.

1. Install dependensi

npm install -D husky lint-staged prettier eslint

Jika proyek Anda memakai TypeScript atau test runner, Anda bisa menyesuaikan dependensi tambahan sesuai kebutuhan proyek.

2. Inisialisasi Husky

npx husky init

Perintah ini biasanya membuat direktori .husky dan hook awal. Setelah itu, Anda bisa mengedit isi hook sesuai workflow tim.

3. Tambahkan script di package.json

{
  "scripts": {
    "dev": "next dev",
    "build": "next build",
    "start": "next start",
    "lint": "next lint",
    "format": "prettier --write .",
    "type-check": "tsc --noEmit",
    "test": "jest"
  },
  "lint-staged": {
    "*.{js,jsx,ts,tsx}": [
      "eslint --fix",
      "prettier --write"
    ],
    "*.{json,css,md}": [
      "prettier --write"
    ]
  }
}

Penjelasannya:

  • next lint dipakai untuk linting berbasis konfigurasi Next.js.

  • tsc --noEmit memeriksa tipe tanpa menghasilkan output build.

  • lint-staged membatasi pemeriksaan ke file staged agar proses commit lebih cepat.

4. Buat hook pre-commit

npx husky add .husky/pre-commit "npx lint-staged"

Jika proyek Anda memakai shell script yang sudah dibuat oleh inisialisasi Husky, cukup pastikan isi file .husky/pre-commit menjalankan npx lint-staged.

Contoh isi file:

npx lint-staged

5. Buat hook pre-push untuk type check atau test

npx husky add .husky/pre-push "npm run type-check && npm run test"

Jika test Anda berat, pertimbangkan hanya menjalankan type check di pre-push, lalu biarkan test lengkap dijalankan di CI.

Contoh konfigurasi yang realistis untuk tim Next.js

Berikut pendekatan yang cukup seimbang untuk banyak tim:

  • pre-commit: jalankan lint-staged untuk file yang berubah.

  • pre-push: jalankan type-check dan subset test yang cepat.

  • CI pipeline: jalankan lint penuh, test penuh, dan build.

Kenapa pembagian ini efektif?

  • Commit tetap cepat sehingga developer tidak terganggu.

  • Masalah dasar ditangkap lebih awal.

  • Validasi yang lebih berat tetap ada sebelum kode masuk lebih jauh.

  • CI tetap menjadi sumber validasi final, bukan digantikan oleh hook lokal.

Contoh kasus nyata yang sering terjadi

Komponen React lolos commit dengan import tidak terpakai

Misalnya developer mengubah komponen di app/ atau components/, lalu lupa menghapus import lama. Hook pre-commit yang menjalankan ESLint akan langsung menggagalkan commit atau bahkan memperbaikinya jika aturan bisa di-fix otomatis.

Developer mengubah tipe data API response

Di Next.js, perubahan pada route handler atau fungsi fetch server-side bisa berdampak ke banyak komponen. Jika return type berubah tetapi pemanggil belum diperbarui, tsc --noEmit pada pre-push akan mendeteksi inkonsistensi sebelum branch dipush.

File .env.local tidak sengaja masuk staging area

Ini sering terjadi saat developer membuat file konfigurasi lokal baru. Anda bisa menambahkan skrip sederhana di hook pre-commit untuk memeriksa apakah ada file sensitif yang akan di-commit.

Contoh sederhana:

if git diff --cached --name-only | grep -E '^(.env|.env.local|.env.production)$'; then
  echo "Commit dibatalkan: file environment sensitif terdeteksi."
  exit 1
fi

Skrip ini bukan solusi keamanan sempurna, tetapi cukup membantu mencegah kesalahan umum.

Pesan commit tidak konsisten dan sulit dipakai untuk release note

Jika tim Anda membuat changelog otomatis, validasi pada hook commit-msg bisa menjaga format commit tetap rapi. Ini bukan kebutuhan semua proyek, tetapi sangat bermanfaat pada tim dengan proses rilis yang terstruktur.

Trade-off dan batasan penggunaan Husky di Next.js

1. Hook yang terlalu berat membuat developer frustrasi

Kesalahan paling umum adalah memasukkan terlalu banyak proses ke pre-commit. Menjalankan build Next.js penuh atau test end-to-end pada setiap commit biasanya terlalu mahal.

Aturan praktis: semakin sering hook berjalan, semakin ringan seharusnya prosesnya.

2. Husky berjalan di mesin lokal, jadi bukan jaminan final

Developer bisa saja melewati hook dengan opsi Git tertentu atau lingkungan lokalnya berbeda. Karena itu, Anda tetap perlu CI untuk validasi final. Husky membantu mempercepat umpan balik, bukan menggantikan proses verifikasi terpusat.

3. Perlu sinkronisasi dengan tool lain

Jika Anda memakai ESLint, Prettier, Jest, Vitest, Playwright, atau alat lain, pastikan script di package.json benar-benar sesuai dengan tool yang dipakai proyek. Jangan menyalin konfigurasi generik tanpa memeriksa apakah script itu valid di repo Anda.

Kesalahan yang sering terjadi

  • Menjalankan lint seluruh proyek di pre-commit. Akibatnya commit lambat, terutama pada repo besar.

  • Mengandalkan Husky tanpa CI. Hook lokal saja tidak cukup untuk menjaga kualitas secara konsisten di tim.

  • Memasukkan test yang tidak stabil ke pre-push. Ini menyebabkan developer sering terblokir oleh flaky test.

  • Tidak mendokumentasikan workflow. Tim baru sering bingung kenapa commit mereka gagal.

  • Tidak mengecualikan file generated. File hasil generate tertentu bisa membuat lint/format tidak relevan atau terlalu lambat.

Tips debugging saat Husky tidak berjalan

Periksa apakah hook benar-benar ada di folder .husky

Pastikan file seperti .husky/pre-commit dan .husky/pre-push memang dibuat dan terisi perintah yang benar.

Pastikan dependensi sudah terpasang

Jika hook memanggil npx lint-staged atau script npm tertentu, pastikan paket terkait memang ada di devDependencies.

Jalankan perintah hook secara manual

Misalnya, jika commit gagal pada lint-staged, jalankan sendiri:

npx lint-staged

Dengan begitu Anda bisa melihat error asli tanpa perantara Git hook.

Periksa script package.json

Sering kali masalahnya bukan di Husky, tetapi pada script seperti npm run type-check atau npm run test yang memang salah atau belum tersedia.

Perhatikan lingkungan shell

Jika tim Anda bekerja lintas sistem operasi, hindari skrip shell yang terlalu spesifik kecuali semua developer memakai lingkungan yang sama. Untuk kebutuhan yang lebih kompleks, kadang lebih aman memakai skrip Node.js daripada shell command murni.

Kapan Husky sebaiknya dipakai, dan kapan tidak perlu berlebihan?

Gunakan Husky jika Anda ingin umpan balik cepat di level lokal, terutama untuk menjaga kualitas dasar seperti lint, format, type safety, dan perlindungan dari commit yang ceroboh. Untuk proyek Next.js yang dikerjakan lebih dari satu orang, ini hampir selalu bermanfaat.

Namun, jangan memakainya untuk semua hal. Build penuh, test end-to-end lengkap, dan validasi yang mahal biasanya lebih cocok dijalankan di CI. Husky efektif jika dipakai secara selektif dan fokus pada pemeriksaan yang paling sering menyelamatkan tim dari kesalahan sehari-hari.

Penutup

Penggunaan Husky di Next.js paling bernilai saat diarahkan ke masalah nyata: menjaga lint tetap bersih, merapikan format otomatis, memeriksa TypeScript sebelum push, menjalankan test cepat, dan mencegah file sensitif ikut ter-commit. Dengan konfigurasi yang ringan di pre-commit dan validasi yang lebih berat di pre-push atau CI, Anda mendapat keseimbangan antara kualitas kode dan kecepatan kerja.

Jika Anda baru mulai, setup paling aman adalah: pre-commit untuk lint-staged, lalu pre-push untuk type-check. Setelah itu, tambah hook lain hanya jika benar-benar menyelesaikan masalah yang memang sering terjadi di proyek Next.js Anda.