Pindah ke App Router Nextjs Bikin Kode Lebih Bersih atau Cuma Kebiasaan Baru Aja
Buat kalian yang sudah lama main di ekosistem Next.js, pasti ingat banget masa-masa Pages Router. Semuanya serba useEffect, useState, dan kalau mau server-side rendering (SSR) atau static site generation (SSG), kita harus pintar-pintar main di getServerSideProps atau getStaticProps. Strukturnya simpel: satu file, satu route.
Lalu datanglah App Router. Sejak Next.js 13 dan semakin matang di Next.js 14, App Router ini bukan cuma sekadar ganti nama folder dari pages jadi app. Ini adalah perubahan paradigma yang mendasar, dipengaruhi oleh konsep React Server Components (RSC).
Pertanyaannya, apakah pindah ke App Router benar-benar membuat kode kita jadi lebih bersih, lebih performa, dan lebih elegan? Atau ini cuma "kebiasaan baru" yang dipaksakan oleh Vercel?
Jawabannya kompleks, tapi secara fundamental, App Router menawarkan potensi kebersihan kode yang jauh lebih tinggi—asalkan kita disiplin dalam memanfaatkannya.
Mengapa App Router Memicu Kode yang Lebih Bersih?
Inti dari App Router adalah pemisahan tegas antara komponen yang berjalan di sisi Server (Next.js server) dan komponen yang berjalan di sisi Client (browser pengguna). Filosofi ini yang menjadi kunci utama kebersihan kode.
1. Server Components sebagai Default
Di Pages Router, semua komponen secara default adalah Client Component. Artinya, meskipun Anda hanya menampilkan data statis, komponen itu tetap harus di-render di sisi klien, memuat JavaScript bundle yang tidak perlu.
Di App Router, semua komponen di dalam folder app secara default adalah Server Components (kecuali jika Anda menambahkan 'use client' di bagian atas file).
Tips Aplikasif (Kode Bersih 101):
Pindahkan Data Fetching ke Server: Tidak perlu lagi library seperti SWR atau React Query hanya untuk mengambil data di halaman utama (kecuali untuk real-time atau stateful fetching*). Dengan Server Components, Anda bisa menggunakan await fetch() langsung di komponen.
javascript
// app/dashboard/page.js (Server Component)
async function getDashboardData() {
// Data fetching langsung tanpa useEffect
const res = await fetch('https://api.myapp.com/data', { cache: 'no-store' });
return res.json();
}Keuntungan: Dengan memindahkan data fetching ke Server, Anda menghilangkan beban dependensi, state management (useState, useEffect) yang biasanya digunakan hanya untuk menampung data awal di sisi klien. Ini menghilangkan boilerplate yang sering membuat kode terlihat kotor. Kode Anda fokus pada rendering, bukan management data fetching.
2. Colocation dan Struktur Routing yang Intuitif
Salah satu keluhan terbesar dari Pages Router adalah pemisahan antara file route (pages/about.js) dan file layout/komponen (components/layout/AboutLayout.js).
App Router memaksa Anda untuk melakukan Colocation. Semua hal yang berhubungan dengan route tertentu ditempatkan dalam folder yang sama.
| File Wajib | Fungsi | Manfaat Kebersihan Kode | | :--- | :--- | :--- | | page.js | Konten unik dari route tersebut. | Fokus murni pada tampilan data. | | layout.js | UI yang dibagi ke semua route di folder tersebut (tidak re-render). | Menghilangkan duplikasi navbar/footer/sidebar di setiap page.js. | | loading.js | UI yang ditampilkan saat data fetching. | Integrasi suspensi (loading state) otomatis, tanpa custom state loading. | | error.js | Boundary error untuk menangani kegagalan. | Pemisahan logika penanganan error yang rapi. |
Dengan struktur ini, Anda tahu persis di mana harus meletakkan kode shared UI (layout.js) dan di mana harus meletakkan logika loading state (loading.js). Keteraturan ini secara otomatis mendorong kode yang lebih terstruktur dan, akibatnya, lebih bersih.
Memahami Batasan: Kapan Harus Pakai 'use client'
Jika Server Components adalah agen pembersih kode, maka 'use client' adalah pengecualian yang harus digunakan dengan bijak. Kesalahan terbesar saat migrasi adalah melabeli komponen Server padahal ia membutuhkan interaksi browser.
Tips Praktis Penggunaan 'use client':
- Hanya Deklarasikan Jika Perlu Interaksi DOM/Browser API: Jika komponen Anda menggunakan
useState,useEffect, event handler sepertionClick, atau membutuhkan akses kewindowataulocalStorage, barulah Anda menambahkan'use client'. - Pisahkan Logika Interaksi: Jangan menjadikan seluruh file sebagai Client Component hanya karena satu tombol membutuhkan
onClick. Pisahkan komponen tersebut menjadi komponen yang lebih kecil:
Parent Component (Server Component): Bertanggung jawab mengambil data dan meneruskannya (sebagai props*). Child Component (Client Component): Hanya menerima props* dan menangani interaksi pengguna.
Contoh sederhana:
javascript
// app/components/ClientButton.jsx
'use client';
import { useState } from 'react';export default function ClientButton({ text }) {
const [count, setCount] = useState(0);
return (
setCount(count + 1)}>
{text} (Clicked {count} times)
);
}// app/page.js (Server Component)
import ClientButton from './components/ClientButton';export default function HomePage() {
// Ini tetap Server Component, jadi bundle JS yang dikirim ke browser minim
return (
Selamat Datang!
{/ Hanya ClientButton yang dikirim ke bundle /}
);
}Pola ini—disebut lifting state atau passing props down—memastikan bahwa bundle JavaScript yang dikirim ke browser sangat kecil dan fokus hanya pada bagian UI yang interaktif. Ini adalah definisi kebersihan kode di era modern web development.
Integrasi Lanjutan dan Tips Migrasi
Migrasi ke App Router memang bukan hanya mengubah nama folder, tetapi juga memerlukan penyesuaian pada beberapa aspek krusial:
3. Penanganan Metadata yang Tepat
Di Pages Router, penanganan metadata (SEO, OG Tags) sering kali memerlukan library pihak ketiga atau manual Head komponen.
Di App Router, penanganan metadata sudah built-in dan dieksekusi di sisi server, yang sangat penting untuk SEO.
javascript
// app/blog/[slug]/page.js
export async function generateMetadata({ params }) {
const post = await getPost(params.slug);return {
title: post.title,
description: post.summary,
openGraph: {
images: [post.image],
},
};
}Manfaat: Kode metadata Anda menjadi colocated dengan route yang bersangkutan dan dijamin render di server, memastikan crawler mendapatkan informasi yang akurat. Kode untuk SEO pun menjadi sangat rapi dan deklaratif.
4. Menggunakan Route Groups untuk Struktur yang Lebih Fleksibel
Seringkali kita ingin memiliki route yang berbagi layout atau konfigurasi tertentu tanpa memengaruhi URL-nya. Di App Router, ini diselesaikan dengan Route Groups menggunakan tanda kurung: (marketing), (dashboard).
app/
├── (marketing)/
│ ├── layout.js (Layout untuk /about dan /contact)
│ ├── about/page.js (/about)
│ └── contact/page.js (/contact)
└── (dashboard)/
├── layout.js (Layout khusus dashboard)
└── settings/page.js (/settings)Manfaat: Struktur ini memungkinkan arsitektur aplikasi yang sangat bersih. Anda bisa memisahkan area publik dari area yang terautentikasi, masing-masing dengan layout dan middleware sendiri, tanpa membuat URL menjadi aneh.
5. Streaming dan Suspense
App Router memanfaatkan Suspense dari React untuk streaming UI ke klien secara bertahap. Ketika Anda menggunakan loading.js, Anda sebenarnya memanfaatkan Suspense.
Tips Praktis: Jangan mencoba meniru loading state di Client Component jika Anda bisa membiarkan loading.js di Server Component yang menanganinya. Ini mengurangi kebutuhan akan state global untuk loading atau state lokal yang rumit, membuat kode Anda lebih ringkas.
Kesimpulan: Cleaner Code, Tapi Butuh Disiplin
Jadi, apakah pindah ke App Router hanya kebiasaan baru? Jelas tidak. App Router adalah evolusi yang sangat signifikan. Ia memaksa developer untuk berpikir server-first, yang mana dalam konteks modern web (di mana performa dan bundle size adalah raja), ini adalah praktik terbaik.
App Router Membuat Kode Lebih Bersih Karena:
- Minimasi Bundle Klien: Dengan Server Components, Anda mengirimkan lebih sedikit JavaScript ke klien, mengurangi boilerplate
useEffectdanuseStateyang hanya berfungsi untuk inisialisasi data. - Struktur yang Terpola: Wajibnya file
layout.js,page.js,loading.js, danerror.jsmenciptakan keteraturan arsitektur yang sangat sulit dicapai di Pages Router tanpa konvensi ketat. - Colocation Logika: Data fetching, metadata, dan middleware berada dekat dengan route yang mereka layani, memudahkan maintenance.
Namun, App Router hanya bersih jika Anda disiplin. Jika Anda asal menambahkan 'use client' di setiap file, Anda pada dasarnya hanya mengimplementasikan Pages Router dengan folder yang berbeda. Kunci kebersihannya adalah memanfaatkan pemisahan Server dan Client secara maksimal.
Javapixa Creative Studio Siap Membantu Transisi Anda
Perubahan paradigma sebesar App Router memang bisa jadi tantangan, terutama bagi tim yang sudah terbiasa dengan Pages Router selama bertahun-tahun. Migrasi yang tidak tepat dapat menyebabkan masalah performa baru atau kebingungan dalam state management.
Di Javapixa Creative Studio, kami telah berinvestasi penuh dalam Next.js App Router dan React Server Components. Kami melihatnya sebagai masa depan high-performance web development. Tim kami ahli dalam merancang arsitektur aplikasi Next.js dari nol, memastikan setiap baris kode yang kami buat memanfaatkan potensi Server Components untuk kecepatan dan kebersihan yang optimal.
Jika Anda berencana memigrasi proyek Next.js Anda yang sudah ada, atau ingin membangun aplikasi baru dengan standar kebersihan kode dan performa tertinggi menggunakan App Router, Javapixa Creative Studio siap menjadi partner Anda. Kami memastikan aplikasi Anda tidak hanya berfungsi, tetapi juga terstruktur dengan rapi, skalabel, dan siap menghadapi tantangan performa di masa depan. Jangan biarkan transisi ke App Router menjadi beban, biarkan ahli yang menangani arsitekturnya.