Menyiapkan fzf agar deterministik di semua mesin: menyimpan opsi FZF_* dan keybindings di repo dotfiles, konfigurasi yang konsisten di bash, zsh, fish, dan nushell, bootstrap otomatis untuk mesin baru, serta checklist produksi yang bisa ditinjau dan diuji.

Di episode 20 kalian meletakkan fzf di tengah ekosistem editor dan developer tools. Episode 21 ini menanyakan pertanyaan yang lebih praktis: apakah setup fzf kalian siap dibawa ke mesin lain? Ketika kalian mendapatkan laptop baru, server baru, atau membuat container dev baru — apakah pengalaman fzf kalian muncul dengan sendirinya, atau harus dikonfigurasi ulang dari nol?
Bayangkan setup fzf sebagai setelan pakaian kerja: nyaman di satu tubuh, tetapi jika tidak diukur ulang, tidak akan pas di tubuh lain. Repo dotfiles adalah "pola jahit" yang menyimpan ukuran itu — dan episode ini membuat pola tersebut deterministik: opsi yang sama, keybinding yang sama, bootstrap yang sama, di mana pun kalian berdiri.
Episode ini membahas struktur dotfiles untuk fzf, manajemen FZF_* dan keybindings, konfigurasi konsisten di bash/zsh/fish/nushell, bootstrap otomatis, dan checklist produksi yang bisa kalian jalankan untuk menguji setup sebelum dibawa ke produksi.
Kunci dari setup fzf yang rapi adalah satu sumber kebenaran untuk opsi, terpisah dari mekanisme per shell. Pola yang banyak dipakai oleh engineer senior:
dotfiles/
├── fzf/
│ ├── fzf.bash
│ ├── fzf.zsh
│ └── fzf.fish
└── .bashrc, .zshrc, config.fishSetiap file per shell berisi tiga hal: integrasi yang dibutuhkan shell itu (fzf dan fzf-tmux yang di-source), variabel FZF_*, dan keybindings opsional. Karena opsi FZF_DEFAULT_OPTS disimpan sebagai string biasa, isinya identik di ketiga file — kalian hanya perlu menjaga konsistensi:
[ -f ~/.fzf.zsh ] && source ~/.fzf.zsh
export FZF_DEFAULT_OPTS="
--height 40%
--layout reverse --border
--multi --cycle
--color fg:-1,bg:-1,hl:208,fg+:-1,bg+:-1,hl+:208
--color info:215,pointer:208,marker:214,prompt:208
"
export FZF_CTRL_T_COMMAND='fd --type f --hidden --follow'
export FZF_CTRL_T_OPTS="--preview 'bat --color=always {}'"Tip
Jika kustomisasi per shell dirasa berlebihan, ada jalan pintas yang valid: set FZF_DEFAULT_OPTS cukup di satu file dan export-kan ke environment — misalnya dari ~/.profile atau file env milik shell manager seperti direnv. Selama shell memuatnya, keybinding bawaan (CTRL-T, CTRL-R, ALT-C) akan memakainya. Tambahan FZF_* per shell hanya diperlukan untuk perilaku yang benar-benar berbeda per shell.
Dotfiles hanya berguna jika bisa dipasang ulang dengan satu perintah. Pola paling sederhana dan paling mudah di-audit adalah script bootstrap yang berurutan:
#!/usr/bin/env bash
set -euo pipefail
command -v fzf >/dev/null || {
echo "memasang fzf..."
git clone --depth 1 https://github.com/junegunn/fzf ~/.fzf
~/.fzf/install --all --key-bindings --completion --no-update-rc
}
ln -sf "$PWD/fzf/fzf.zsh" ~/.fzf.zsh
ln -sf "$PWD/fzf/fzf.bash" ~/.fzf.bash
ln -sf "$PWD/fzf/fzf.fish" ~/.fzf.fishTiga sifat yang harus dimiliki setiap bootstrap:
ln -sf dipakai untuk menimpa symlink, bukan ln -s.Note
Untuk mesin tanpa internet atau tanpa hak sudo, bootstrap bisa memakai paket yang sudah tersedia: apt install fzf, pacman -S fzf, brew install fzf, atau apk add fzf. Sesuaikan branch install di script bootstrap kalian dengan platform target — dan catat asumsinya di komentar README, bukan di dalam script.
Setiap shell punya cara memuat integrasi fzf yang berbeda, dan kegagalan paling umum pada setup lintas shell adalah mencampur sintaks. Mari petakan:
| Shell | Memuat integrasi fzf | Sintaks keybinding |
|---|---|---|
| bash | source ~/.fzf.bash di .bashrc | Ctrl-T, Ctrl-R, Alt-C |
| zsh | source ~/.fzf.zsh di .zshrc | sama seperti bash |
| fish | fzf_key_bindings setelah fzf.fish di-source | Ctrl-T, Ctrl-R, Alt-C |
| nushell | fzf --nushell menghasilkan module yang di-source | Ctrl-T, Ctrl-R, Alt-C |
Perhatikan bahwa keybinding default (CTRL-T, CTRL-R, ALT-C) identik di keempat shell — konsistensi itulah yang membuat otot kalian tidak perlu belajar ulang saat berpindah mesin. Yang berbeda hanyalah cara memuatnya:
if command -q fzf
fzf --fish | source
fzf_key_bindings
endsource ($"{(^fzf --nushell | to text)}"Important
Jangan menyalin snippet satu shell ke shell lain tanpa menyesuaikan. fzf --fish | source tidak bisa dieksekusi di bash, dan source ~/.fzf.zsh tidak akan berfungsi di fish. Biarkan fzf membangkitkan integrasinya sendiri untuk setiap shell (fzf --bash, fzf --zsh, fzf --fish, fzf --nushell) — itulah cara yang dijamin konsisten antar versi.
Setiap proyek bisa meminta perilaku fzf yang berbeda — dan konfigurasi global tidak boleh dipaksa menyatukan semuanya. Di episode 8 kalian belajar opsi di FZF_DEFAULT_OPTS; di sini polanya diperluas dengan konfigurasi berlapis:
FZF_DEFAULT_OPTS): opsi yang selalu masuk akal — height, layout, warna, border.FZF_CTRL_T_OPTS, FZF_CTRL_R_OPTS): penyesuaian untuk keybinding tertentu._local milik proyek.Prinsipnya: global itu minimal, spesifik itu eksplisit. Ketika kalian menambah opsi global, tanyakan "apakah ini masuk akal untuk semua proyek?" Jika tidak, opsi itu bukan untuk global.
FZF_DEFAULT_OPTS='--color fg:120,pointer:120,hl:120' fzfTip
Cara terbaik untuk menguji apakah sebuah opsi pantas menjadi global: gunakan selama satu minggu di semua proyek. Jika tidak ada proyek yang merasa terganggu, promosikan ke FZF_DEFAULT_OPTS. Jika ada yang menolak, simpan sebagai konfigurasi khusus. Produksi adalah hasil dari pemakaian berulang, bukan dari perencanaan di depan.
Setup yang siap produksi bisa diuji dengan checklist yang deterministik — bukan diukur dari "terasa nyaman", melainkan dari hasil yang bisa diverifikasi. Jalankan ini setiap kali menyetel ulang mesin:
| # | Cek | Perintah verifikasi |
|---|---|---|
| 1 | Binary terpasang | fzf --version |
| 2 | Integrasi shell ter-load | ketik echo $FZF_DEFAULT_OPTS — tidak kosong |
| 3 | Keybindings aktif | tekan Ctrl-T di shell |
| 4 | Preview berfungsi | fd -t f | fzf --preview 'bat --color=always {}' |
| 5 | History search jalan | Ctrl-R membuka fzf, bukan prompt bawaan |
| 6 | Shell integration vim/nvim jalan | vim mengenal FZF_DEFAULT_COMMAND bila diset |
| 7 | Versi konsisten antar mesin | bandingkan fzf --version dengan baseline tim |
| 8 | fzf-tmux bekerja | fzf-tmux -p 60% membuka panel tanpa error |
Checklist ini sengaja pendek — delapan cek yang menjawab satu pertanyaan: "apakah pengalaman fzf yang sama muncul di mesin ini?" Jika ada yang gagal, catat di README dotfiles, bukan hanya diperbaiki sekali.
Warning
Versi yang tidak konsisten antar mesin adalah sumber bug paling halus. --listen di mesin A bisa bekerja karena 0.70+, sementara mesin B yang masih 0.69 gagal diam-diam. Untuk tim, pin baseline di file dotfiles — misalnya komentar # fzf >= 0.74.1 — dan jadikan fzf --version bagian dari bootstrap verification.
| Kesalahan | Gejala | Solusi |
|---|---|---|
| Mencampur sintaks shell | Keybinding error di satu shell saja | Pakai fzf --bash/zsh/fish/nushell sesuai shell |
| Bootstrap tidak idempoten | Menjalankan dua kali menumpuk file | Gunakan ln -sf, bukan ln -s |
| Opsi global terlalu banyak | Proyek tertentu terasa aneh | Pertahankan global minimal; spesifik per proyek |
| Keybinding hilang di zsh | source ~/.fzf.zsh terlewat | Panggil di .zshrc, bukan di .bashrc |
| Preview gagal di mesin baru | bat tidak terpasang | Checklist: verifikasi preview sebelum produksi |
| Versi fzf tidak konsisten | Perilaku berbeda antar mesin | Pin baseline di README dotfiles |
Pada episode 21 ini kalian menyiapkan fzf agar deterministik lintas mesin: struktur dotfiles dengan satu sumber kebenaran per shell; bootstrap idempoten yang memasang binary lalu menghubungkan konfigurasi; konsistensi keybinding di bash, zsh, fish, dan nushell lewat integrasi yang dibangkitkan fzf sendiri; konfigurasi berlapis global-per-proyek; serta checklist produksi delapan langkah yang bisa diverifikasi setiap kali mesin disetel ulang.
Pesan untuk dibawa pulang: setup fzf yang produksi-ready bukan yang paling mewah, melainkan yang paling deterministik — bisa dipasang ulang, diuji, dan diaudit dengan perintah yang sama di mana pun.
Setelah menempuh 21 episode, waktunya melihat ke belakang — dan ke samping. Di episode terakhir, episode 22, kita membahas ekosistem alternatif & refleksi akhir: membandingkan fzf dengan skim, percol, peco, pick, dan fzy; mengenal fzf sebagai library Go; merangkum perjalanan episode 0 sampai 21; serta menutup series dengan checklist daily driver dan pesan untuk dibawa pulang.