author Ahmad Muhardian

Proses Migrasi Template Petani Kode dari Bootstrap ke Tailwind


Hugo Bootstrap Tailwind

Setelah dulu mengganti template menggunakan Bootstrap, kini kita ganti dengan Tailwind.

Mengapa memilih tailwind?

Gimana proses migrasinya?

dan gimana perbandingan setelah migrasi?

Mari kita bahas..

Mengapa Memilih Tailwind?

Saya memilih Tailwind karena:

1. Utility Based

Alasan pertama karena Tailwind mungkin satu-satunya framework yang berbasis Utility. Sedangkan framework yang lainnya kebanyakan berbasis komponen.

Bootstrap memang punya class utility, tapi tidak sebanyak Tailwind. Class-class di Tailwind 100% adalah Utility.

Ini membuat kita bebas membuat komponen sendiri. Ada juga sih komponen yang udah jadi seperti daisyUI, tapi saya lebih senang membuatnya dari nol.

2. Ukuran Filenya Kecil

Ini mungkin karena Tailwind menggunakan PurgeCSS.

Jadi class-class yang tidak terpakai, tidak akan ditambahkan pada CSS hasil build. Ini membuat CSS-nya lebih kecil.

Berbeda dengan CSS framework yang berbasis komponen. Walaupun kita tidak pakai komponen tertentu, maka class-nya akan tetap ikut ditambahkan di file CSS.

Dulu saya pernah coba PurgeCSS di Bootstrap, tapi hasilnya tidak maksimal. beberapa komponen tidak bisa bekerja dengan normal.

Karena itu, mungkin CSS Framework yang berbasis komponen kurang cocok dipakein PurgeCSS.

Meski terasa mubazir, mau tidak mau harus rela membiarkan class yang tidak terpakai tetap berada di dalam file CSS production.

…dan membebani ukuran file.

Berikut ini perbandingan hasil build tema petani kode menggunakan Bootstrap dan Tailwind.

Perbedaan hasil build tailwind dengan bootstrap

Sangat beda jauh perbandingan ukurannya. πŸ˜„

3. Cocok dipakai dengan Alpinejs

Alpinejs sudah lama saya pakai sebagai pengganti JQuery. Pada template sebelumnya saya juga pakai si Alpine dengan Bootstrap.

Alpinejs memang bisa dipakai dengan framework apapun, tapi kayaknya lebih cocok dengan Tailwind.

Dulu pernah coba mau ganti Javascript yang dipakai Bootstrap untuk menampilkan Modal dengan Alpine, tapi saya rasa cukup sulit.

Berbeda ketika pakai Tailwind, rasanya lebih mudah.. πŸ˜„ mungkin ini cuma perasaan saya aja, belum 100% benar.

4. Lagi Populer

Tailwind memang begitu populer belakangan ini. Banyak web yang mengadopsinya dan review-review-nya menjanjikan.

Baru saja saya dengar kalau Google IO 2022 juga menggunakan TailwindCSS

Wow, developer Google sampai menggunakan Tailwind, berarti ini keren.

5. Karena ingin Belajar Tailwind

Alasan terakhir karena saya memang ingin belajar Tailwind.

Dulu memang pernah pakai saat masih versi 1, tapi hasil build-nya saya rasa masih kurang optimal. Tidak sebagus sekarang yang versi 3.

Atau mungkin saya yang kurang tau cara build-nya dulu πŸ˜„..

Sekarang belajar lagi, mengenal dan membiasakan diri menggunakan class-class Tailwind.

Proses Migrasi

Proses migrasi saya kerjakan selama lima hari.

Saya biasanya mengerjakan setelah sahur (jam 4) sampai jam 10 pagi dan malam hari sehabis tarawih sempai 10 malam.

1. Hari Pertama

Pada hari pertama, saya mulai membuat tema baru dengan mengikuti tutorial:

Kode temanya benar-benar dibuat dari nol, tapi ada juga sih yang di-copas dari tema sebelumnya dan tinggal mengganti class-nya.

Todo list hari ini:

  • membuat template untuk home page (index.html)
    • Navbar Section
    • Header Section
    • Post List Section
    • Newsletter Section
    • Footer Section

Hari ini saya cuma mengerjakan satu halaman saja, yakni home page.

Jujur, saya masih merasa kesulitan menggunakan Tailwind, karena ini baru pertama kalinya menggunakan Tailwind di real project.

Dulu memang pernah belajar sedikit, tapi lupa.

..dan akhirnya belajar lagi sekarang 😄.

Hasil coding hari ini berupa halaman home yang masih belum responsive. Apa bila dibuka pakai HP, pasti akan berantakan.

halaman home

Tapi tidak masalah, ini akan saya perbaiki di hari berikutnya.

2. Hari Kedua

Pada hari kedua ini, saya melanjutkan lagi apa yang belum selesai kemarin.

Todo List hari ini:

  • Perbaiki Reponsive
  • Buat fitur Dark Mode
  • Buat template halaman Post (list.html dan single.html)
  • Buat template halaman tutorial (list.html dan single.html)

Saya mulai memperbaiki responsive dengan menerapkan modifier xs, sm, md, dan sebagainya.

Setelah bolak-balik membaca dokumentasi Tailwind, saya tambah paham gimana cara membuat layout di Tailwind.

Ternyata ada yang sama dan beda dengan Bootstrap.

Di Tailwind dan Bootstrap sama-sama ada class .container tapi punya cara pakai yang berbeda. Class .container di Tailwind harus digunakan bersama class mx-auto dan max-w-* agar bisa tampil di tengah-tengah dengan ukuran tertentu.

Setelah selesai memperbaiki responsif di halaman home, saya melanjutkan mengerjakan fitur dark mode.

Ada dua cara yang dipakai untuk bikin Dark Mode di Tailwind:

  1. Menggunakan Media Query
  2. Menggunakan Class

Saya memilih menggunakan yang ke-2, karena bisa diatur secara manual. Sedangkan cara yang pertama diatur otomatis mengikuti settingan device.

Saya menggunakan AlpineJS untuk membuat toggle Dark Mode secara reaktif.

Setelah selesai mengerjakan Dark Mode, saya lanjut mengerjakan template untuk halaman lain seperti halaman Post dan Tutorial.

Oya, Saya menggunakan plugin Prose untuk Typography di artikel.

Hari ini saya mendapatkan hasil yang cukup memuaskan dan saya mulai terbiasa menggunakan Tailwind setelah menghabiskan berjam-jam ngoprek si Tailwind.

3. Hari Ketiga

Pada hari ketiga, saya melanjutkan membuat template untuk widget seperti Recent Post, Newsletter, Iklan di sidebar, dan lain-lain.

To do list hari ini:

  • Widget Newsletter di Sidebar
  • Widget Recent Post di SIdebar
  • Iklan di Sidebar
  • Iklan Sticky di Sidebar
  • Menambahkan Lightbox untuk gambar
  • Mengganti Turbolinks dengan Turbo

Turbolinks saya ganti karena project-nya sudah berhenti dan digantikan Turbo dari Hotwired.

4. Hari Keempat

Pada hari ke-4 saya melanjutkan mengerjakan template halaman yang belum dikerjakan seperti halaman 404, pencarian, taxonomy, dll.

To do list hari ini:

  • Halaman Error 404 Not found
  • Halaman Search
  • Halaman Taxonomy (Post List)
  • Halaman Taxonomy (Terms List)
  • Halaman Author
  • Halaman List Author

Hari ini saya cuma bisa mengerjakan sampai halaman taxonomy, sementara untuk halaman Author akan dikerjakan di hari berikutnya.

5. Hari Kelima

Pada hari ini saya melanjutkan pekerjaan yang belum selesai kemarin.

To do list hari ini:

  • Membuat halaman List Author
  • Membuat halaman Author Detail
  • Menerapkan auto testing framework
  • Menulis konten ini

Selain membuat halaman Author, saya juga menambahkan testing Framework menggunakan Cypress.io.

Sebenarnya testing belum begitu perlu sih untuk kasus ini, karena cuma halaman blog saja, bukan aplikasi.

Tapi ada beberapa fitur yang ingin saya pastikan bekerja dengan benar seperti:

Jadi testingnya seputar tiga fitur itu aja.

Sementara untuk fitur lainnya seperti Newsletter dan pencarian, tidak perlu dites karena di-handle oleh pihak ketiga.

Hasil tes Dark Mode dan Side Navbar:

Hasil tes Lightbox:

Masalah dan error yang dialami

Selama pengerjaan tentu tidak berjalan mulus, pasti ada aja error dan masalahnya.

Nah berikut ini masalah dan error yang saya temui saat melakukan migrasi.

Perbedaan Versi Nodejs

Tailwind CSS dan PostCSS dijalankan menggunakan Nodejs di belakang layar. Perbedaan versi Nodejs yang saya gunakan kadang membuat build-nya gagal.

Tidak ada pesan error yang ngasih tau kalau error-nya disebabkan karena perbedaan versi.

error versi nodejs

Kadang ini membuat saya bingung, sebelumnya berjalan lancar. Tapi setelah membuka kembali project menjadi error seperti di atas.

Ini karena di awal saya menggunakan Node v18.0.0, kemudian setiap saya menutup project.. versi nodejs-nya akan otomatis diganti ulang ke v12.14.0.

Solusinya:

Ubah versi nodejs dengan nvm. Ini solusi sementara, solusi jangka panjangnya mungkin harus menginstal ulang atau upgrade nodejs ke versi v18.0.0.

nvm-use-nodejs

Jika ingin permanen gunakan perintah:

nvm alias default 18

Solusi lainnya, bisa menambahkan properti "engine" pada package.json seperti ini:

"engines": {
  "npm": ">=8.0.0",
  "node": ">=18.0.0",
  "yarn": ">=1.22.4"
},

Setelah itu tambahkan file .npmrc di root folder project dengan isi sebagai berikut.

engine-strict=true

Ini bertujuan agar kita wajib menggunakan Node v18.0.0 di project ini. Jika tidak menggunakan versi ini, maka kita akan dapat pesan error seperti ini:

error [email protected]: The engine "node" is incompatible with this module. Expected version ">=18.0.0". Got "12.14.0"
error Commands cannot run with an incompatible environment.

Hasil Render Tidak Langsung Kelihatan

Saat menggunakan class Tailwind baru yang belum pernah dipakai sebelumnya, hasilnya tidak akan langsung kelihatan saat hot reload.

Ini karena class tersebut belum ditambahkan ke file CSS hasil build. Mungkin karena Hugo tidak melakukan build ulang saat hot reload.

Solusinya:

Harus menjalankan ulang server agar CSS-nya di-build ulang atau gunakan Tailwind yang CDN saat development.

Contohnya seperti ini:

{{ if hugo.IsServer }}
<!-- Gunakan Tailwind dari CDN -->
<script src="https://cdn.tailwindcss.com"></script>
<script src="https://cdn.tailwindcss.com?plugins=forms,typography,aspect-ratio,line-clamp"></script>
<script>
  tailwind.config = {
    darkMode: "class",
  }
</script> 
{{ else }}
<!-- gunakan Tailwind dari hasil build -->
{{ $styles := $styles | minify | fingerprint | resources.PostProcess }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Integrity }}" data-turbo-track="reload"/>
{{ end }}

Jadi saat menjalankan server Hugo, Tailwind yang dipakai adalah Tailwind yang dari CSS sedangkan ketika build site untuk production, yang dipakai adalah Tailwind hasil build.

Solusi ke-2:

Solusi lain, kita bisa build secara manual CSS tailwind-nya, kemudian outputnya di simpan ke dalam folder static/css/.

Untuk melakukan ini saya membuat script baru di package.json seperti ini:

{
  // ...
  "scripts": {
    "start": "hugo server",
    "draft": "hugo server -D",
    "tailwind:watch": "npx tailwindcss -i ./themes/petanikode-tailwind/assets/css/main.css -o ./themes/petanikode-tailwind/static/css/main.css --watch",
    "build": "NODE_ENV=production hugo --minify",
    "clean": "rimraf public",
    "test:server": "http-server public --silent --port 1313",
    "test:gui": "npx cypress open",
    "test": "npx cypress run --quiet"
  }
  // ...
}

Kemudian di <head>, tinggal dibuat seperti ini:

{{ $styles := resources.Get "css/main.css" | postCSS }}

{{ if hugo.IsServer }}
<link rel="stylesheet" href="/css/main.css" />
{{ else }}
{{ $styles := $styles | minify | fingerprint | resources.PostProcess }}
<link rel="stylesheet" href="{{ $styles.RelPermalink }}" integrity="{{ $styles.Data.Integrity }}" />
{{ end }}

Dengan demikian CSS yang akan dipakai saat menjalankan server adalah CSS hasil build dari Tailwind.

Tapi kekurangannya, kita harus menjalankan dua perintah dalam dua terminal.

dua terminal

Namun, untungnya masalah ini bisa diselesaikan dengan run-p.

Atau bisa juga dengan membuat command baru seperti ini:

"dev": "hugo server & yarn tailwind:watch && fg"

Note: ini cuma berlaku di Linux atau Unix like.

Ada Tutup Komentar yang Ketinggalan

Ini lucu sih, entah komentar yang mana yang belum ditutup. Saya membutuhkan waktu cukup lama untuk mengetahui letaknya.

error-tutup-komentar

Hasil inspect element

inspect-error-tutup-komentar

Mungkin error-nya di sekitaran situ.

dan ternyata benar di sini masalahnya:

tutup-komentar-pada-kode

Class Kadang Sering Diulang (Duplikat)

Kadang saya sering menulis ulang class yang sama di satu tempat.

class duplicate

Ini biasanya terjadi saat melakukan edit dan menambahkan class.

Tapi tenang saja, kita bisa atasi dengan extension Tailwind di VS Code.

Nama extension-nya: Tailwind CSS IntelliSense

Kita akan dikasih tau kalau ada error atau penulisan yang duplikat.

plugin tailwind

Perbandingan Before After

Berikuti ini perbandingan before migrasi dan after migrasi ke Tailwind.

Before dan After Tampilan

Home page before:

home before

Home page after:

home page after

Navbar before:

navbar before

Navbar after:

navbar after

Footer before:

footer-before

Footer after:

footer after

Post page before:

post page before

Post page after:

post page after

Before dan After Hal Teknis

ToolsBeforeAfter
CSS FrameworkBootstrapTailwind CSS
Testing Framework-Cypress.io
CSS ProcessorSASSPostCSS
IconsBootstrap IconsHeroicons
PWA ToolsTurbolinksTurbo by Hotwired
Javascript Framework/LibsAlpinejs, JQuery, Popper.jsAplinejs

Apa Selanjutnya?

Saya rasa template ini masih belum 100% selesai dan akan terus dikembangkan lagi.

Gimana pendapatmu tentang template baru ini?