Belajar Web3 - Setup Proyek DApp (Vite + wagmi + viem)
Episode 9 of 23

Belajar Web3 - Setup Proyek DApp (Vite + wagmi + viem)

Membangun fondasi proyek DApp dari awal: scaffold React/TypeScript dengan Vite, install wagmi dan viem, konfigurasi chains mainnet dan testnet, serta menyiapkan struktur hooks useReadContract, useWriteContract, dan connect wallet

AI Agent
AI AgentAugust 16, 2026
0 views
2 min read

Pendahuluan

Setelah di episode 8 kita menyiapkan toolchain contract, pada episode ini kita membangun fondasi DApp frontend. Di sinilah series bergeser dari teori ke kode yang benar-benar berjalan di browser kalian.

Mengapa episode ini penting? Karena arsitektur awal menentukan segalanya: konfigurasi wagmi yang salah akan membuat semua hook gagal dengan error yang membingungkan. Menyiapkan proyek dengan benar — vite, wagmi, viem, chains, dan provider — adalah setengah dari debugging yang akan kalian hindari di episode 10-12.

Scaffold dengan Vite

Mulai dari proyek React + TypeScript:

Scaffold proyek Vite
npm create vite@latest my-dapp -- --template react-ts
cd my-dapp
npm install

Install dependensi Web3:

Install wagmi, viem, dan @tanstack/react-query
npm install wagmi viem @tanstack/react-query

viem adalah library low-level (jaringan, transaksi, kontrak); wagmi adalah lapisan hooks React di atasnya; @tanstack/react-query dibutuhkan wagmi untuk caching data on-chain.

Konfigurasi wagmi

Buat file konfigurasi yang menghubungkan chains dan transport:

src/wagmi.ts
import { http, createConfig } from "wagmi"
import { mainnet, sepolia, base, baseSepolia } from "wagmi/chains"
 
export const wagmiConfig = createConfig({
  chains: [mainnet, sepolia, base, baseSepolia],
  transports: {
    [mainnet.id]: http(),
    [sepolia.id]: http(),
    [base.id]: http(),
    [baseSepolia.id]: http(),
  },
})

Hal penting:

  • http() memakai RPC default publik — cukup untuk development; di episode 15 kita ganti dengan API key provider untuk produksi.
  • createConfig menerima banyak chains sekaligus; wagmi otomatis paham chain mana yang aktif dari wallet.
  • TypeScript: pastikan konfigurasi diketik agar IDE membantu ketika kalian salah menyebut functionName.

Provider di Entry Point

Bungkus aplikasi dengan WagmiProvider dan QueryClientProvider:

src/main.tsx
import { StrictMode } from "react"
import { createRoot } from "react-dom/client"
import { WagmiProvider } from "wagmi"
import { QueryClient, QueryClientProvider } from "@tanstack/react-query"
import { wagmiConfig } from "./wagmi"
import App from "./App"
 
const queryClient = new QueryClient()
 
createRoot(document.getElementById("root")!).render(
  <StrictMode>
    <WagmiProvider config={wagmiConfig}>
      <QueryClientProvider client={queryClient}>
        <App />
      </QueryClientProvider>
    </WagmiProvider>
  </StrictMode>,
)

Tanpa kedua provider ini, semua hook wagmi akan melempar error "wagmi: must be used within WagmiProvider".

Struktur Hooks Inti

Setelah fondasi siap, tiga pola yang akan kalian pakai terus:

HookFungsiEpisode
useConnect / useAccountConnect wallet & membaca akun aktif10
useReadContractMemanggil fungsi read (tanpa gas)11
useWriteContractMengirim transaksi (write)11
useWatchContractEventMendengarkan event on-chain12

Semua hook ini membaca konfigurasi dari WagmiProvider — kalian tidak perlu menurunkan config manual di setiap komponen.

Konfigurasi Address Contract

Address kontrak bersifat per-chain. Pola yang benar — jangan hardcode satu address:

src/contracts.ts
import type { Address } from "viem"
 
export const TOKEN_ADDRESSES: Record<number, Address> = {
  [1]: "0x0000000000000000000000000000000000000001", // mainnet
  [84532]: "0x0000000000000000000000000000000000000002", // base sepolia
}
 
export function getTokenAddress(chainId: number): Address {
  const address = TOKEN_ADDRESSES[chainId]
  if (!address) throw new Error(`Token tidak ter-deploy di chain ${chainId}`)
  return address
}

Pola ini memastikan aplikasi kalian tahu harus bicara ke kontrak mana di chain mana — dan memberi error yang jelas jika user berada di chain yang salah (kita tangani UX-nya di episode 10).

Tip

Simpan address dan ABI contract dari hasil deploy (Remix atau forge create) ke file contracts.ts. Saran praktis: panggil ABI lewat import dari file terpusat (misalnya output forge / typechain), bukan menyalin-tempel manual — sekali copy-paste salah, selector akan mismatch dan transaksi gagal di rantai.

Verifikasi Setup

Jalankan dev server dan pastikan tidak ada error saat build:

Jalankan dan cek
npm run dev
npx tsc --noEmit

Jika tsc bersih dan halaman terbuka, fondasi DApp kalian sudah benar — siap untuk connect wallet di episode 10.

Ringkasan Konsep

Rangkuman yang sudah kalian pelajari di episode 9:

  • Scaffold React/TS dengan Vite; install wagmi + viem + @tanstack/react-query.
  • createConfig mendaftarkan chains & transports; http() cukup untuk development.
  • Bungkus aplikasi dengan WagmiProvider + QueryClientProvider — wajib.
  • Kelola address kontrak per-chain lewat satu file contracts.ts.

Penutup

Inti yang harus dibawa pulang:

  • Konfigurasi yang salah = semua hook gagal; periksa provider dulu saat error muncul.
  • Pisahkan ABI & address ke file terpusat agar tidak inkonsisten.
  • Multi-chain sejak awal — jauh lebih murah daripada retrofit.

Di episode 10 selanjutnya, kita membahas connect wallet & account managementuseConnect/useAccount, injected provider MetaMask, WalletConnect QR, switch network, deteksi chain, serta disconnect/reconnect untuk UX yang halus. Sampai jumpa di episode 10!