Programmer

Fitur Baru Vue 3.5: Memori Lebih Hemat & Reactive Props

–

vue

Vue.js terus berkembang sebagai salah satu framework JavaScript yang banyak digunakan untuk membangun antarmuka web modern. Setelah beberapa versi sebelumnya berfokus pada penyempurnaan Composition API, TypeScript, dan pengalaman developer, Vue 3.5 hadir dengan pendekatan yang cukup menarik. Rilis ini bukan sekadar menambahkan beberapa API baru, tetapi juga membawa perombakan internal pada sistem reaktivitas yang berdampak pada penggunaan memori dan performa aplikasi.

Vue 3.5 dirilis sebagai minor release tanpa perubahan API yang bersifat breaking secara umum. Namun, perubahan internal di dalam sistem reaktivitasnya tergolong besar. Tim Vue melakukan refactor pada mekanisme dependency tracking sehingga penggunaan memori internal dapat berkurang hingga 56% dalam pengujian yang menjadi dasar pengumuman rilis tersebut. Selain itu, operasi pada array reaktif berukuran besar dan sangat dalam dapat menjadi jauh lebih cepat dalam skenario tertentu.

Perubahan lain yang sangat terasa bagi developer adalah Reactive Props Destructure yang akhirnya stabil. Sebelumnya, melakukan destructuring pada hasil defineProps() dapat membuat developer harus berhati-hati agar reaktivitas tidak hilang. Pada Vue 3.5, compiler Vue menangani pola tersebut sehingga props yang di-destructure di dalam <script setup> tetap dapat mengikuti perubahan dari parent component.

Bagi developer yang mengembangkan dashboard, aplikasi SaaS, sistem administrasi, e-commerce, aplikasi data, atau proyek Vue dengan jumlah komponen yang besar, perubahan tersebut cukup penting. Performa yang lebih baik tidak hanya berarti aplikasi lebih cepat, tetapi juga dapat mengurangi beban memori dan pekerjaan optimasi manual.

Apa Itu Vue 3.5?

Vue 3.5 adalah pembaruan minor dari Vue 3 yang membawa sejumlah penyempurnaan pada core framework, Composition API, sistem reaktivitas, server-side rendering, dan pengalaman developer.

Berbeda dari rilis yang membawa perubahan besar pada API, Vue 3.5 mempertahankan banyak pola pengembangan yang sudah digunakan pada Vue 3. Fokusnya lebih banyak berada pada peningkatan internal dan penambahan fitur yang membuat kode menjadi lebih sederhana.

Salah satu perubahan terpenting berada pada reactivity system. Vue menggunakan sistem reaktivitas untuk mengetahui kapan sebuah data berubah dan bagian aplikasi mana yang perlu diperbarui.

Sebagai contoh, ketika sebuah nilai ref berubah, Vue perlu mengetahui komponen, computed, atau watcher mana yang menggunakan nilai tersebut. Proses untuk menghubungkan sumber data dengan pengguna data tersebut disebut dependency tracking.

Pada aplikasi kecil, proses tersebut biasanya tidak menjadi masalah. Namun, pada aplikasi besar yang memiliki ribuan reactive state, computed property, watcher, dan komponen, jumlah hubungan dependency dapat menjadi sangat besar.

Karena itu, Vue 3.5 melakukan perubahan pada struktur internal dependency tracking untuk membuat pengelolaannya lebih efisien.

Sistem Reaktivitas Vue 3.5 Lebih Efisien

Reactivity system merupakan salah satu bagian paling penting dalam Vue. Sistem ini memungkinkan Vue mendeteksi perubahan data dan kemudian menjalankan proses yang diperlukan untuk memperbarui tampilan.

Secara sederhana, hubungan tersebut dapat dibayangkan seperti:

Data berubah -> dependency terdeteksi -> effect dijalankan -> tampilan diperbarui

Masalahnya, aplikasi modern dapat mempunyai hubungan dependency yang sangat kompleks. Satu reactive state bisa digunakan oleh beberapa computed property, watcher, dan komponen sekaligus.

Vue 3.5 melakukan refactor pada sistem tersebut untuk mengurangi overhead internal.

Apa yang Dimaksud dengan Dependency Tracking?

Dependency tracking adalah mekanisme yang digunakan Vue untuk mengetahui data apa yang digunakan oleh suatu reactive effect.

Contohnya:

<script setup>
import { ref, computed } from 'vue'

const count = ref(0)

const doubleCount = computed(() => {
  return count.value * 2
})
</script>

Dalam contoh tersebut, doubleCount bergantung pada count.

Ketika count.value berubah, Vue perlu mengetahui bahwa doubleCount memiliki hubungan dengan data tersebut. Vue kemudian dapat menghitung ulang computed ketika diperlukan.

Pada aplikasi besar, hubungan seperti ini dapat berjumlah sangat banyak. Karena itu, struktur data yang digunakan untuk menyimpan hubungan tersebut mempunyai pengaruh terhadap efisiensi memori dan performa.

Perombakan Internal dengan Struktur Linked List

Vue 3.5 melakukan refactor besar pada struktur dependency tracking. Implementasinya menggunakan pendekatan yang lebih efisien dengan hubungan berbentuk doubly linked list atau linked list dua arah, bersama mekanisme internal lainnya untuk mengelola hubungan dependency dan subscriber.

Doubly linked list merupakan struktur data yang memungkinkan sebuah node mengetahui node sebelum dan sesudahnya.

Dalam konteks reaktivitas, struktur tersebut membantu Vue mengelola hubungan antara dependency dan subscriber secara lebih efisien. Developer tidak perlu mengubah cara menggunakan ref(), reactive(), computed(), atau watch() karena perubahan tersebut berada di level internal framework.

Artinya, keuntungan performa bisa diperoleh tanpa harus menulis ulang seluruh kode aplikasi.

Penggunaan Memori Berkurang hingga 56 Persen

Salah satu angka yang paling banyak dibicarakan dari Vue 3.5 adalah pengurangan penggunaan memori hingga 56% pada sistem reaktivitas.

Angka tersebut bukan berarti semua aplikasi Vue otomatis menggunakan 56% lebih sedikit RAM. Ini merupakan hasil pengukuran terhadap overhead sistem reaktivitas pada skenario benchmark tertentu.

Perbedaan tersebut penting untuk dipahami agar klaim performa tidak disalahartikan. Aplikasi sederhana dengan sedikit reactive state belum tentu mengalami penurunan penggunaan RAM sebesar itu.

Sebaliknya, manfaatnya lebih relevan untuk aplikasi yang mempunyai jumlah dependency reaktif yang besar dan struktur data kompleks.

Computed Lebih Aman dari Stale Value

Vue 3.5 juga memperbaiki sejumlah masalah internal berkaitan dengan computed yang sudah tidak digunakan tetapi masih memiliki hubungan dependency.

Stale computed dapat dipahami sebagai kondisi ketika nilai atau dependency lama masih tersimpan dalam sistem meskipun seharusnya tidak lagi digunakan.

Perbaikan pada sistem reaktivitas membantu Vue menangani kondisi tersebut dengan lebih baik. Pengumuman Vue 3.5 juga menyebutkan bahwa refactor ini menyelesaikan masalah stale computed dan masalah memori yang berkaitan dengan computed yang menggantung, termasuk dalam skenario SSR.

Optimasi Array Reaktif

Selain penggunaan memori, Vue 3.5 juga meningkatkan tracking untuk array reaktif yang besar dan memiliki struktur dalam.

Array merupakan struktur data yang sangat umum digunakan dalam aplikasi Vue. Contohnya adalah:

  • daftar produk
  • tabel transaksi
  • daftar pengguna
  • data laporan
  • hasil pencarian
  • notifikasi
  • data dashboard
  • daftar pesan

Pada aplikasi sederhana, perubahan array tidak menjadi masalah besar. Tetapi ketika array berisi banyak data dan objek di dalamnya juga bersifat reaktif, proses tracking dapat menjadi lebih kompleks.

Vue 3.5 mengoptimalkan kondisi tersebut dan dalam beberapa skenario operasi pada array reaktif yang besar dapat menjadi hingga 10 kali lebih cepat.

Angka tersebut tetap harus dibaca sebagai hasil pada skenario tertentu, bukan jaminan bahwa setiap operasi array di semua aplikasi akan menjadi 10 kali lebih cepat.

Namun, bagi aplikasi dengan data dalam jumlah besar, optimasi ini dapat menjadi keuntungan yang cukup signifikan.

Reactive Props Destructure Menjadi Stable

Jika ada satu fitur Vue 3.5 yang kemungkinan besar langsung terasa ketika menulis kode, fitur tersebut adalah Reactive Props Destructure.

Props adalah data yang dikirim dari parent component ke child component.

Misalnya:

<ChildComponent
  :count="total"
  msg="Halo"
/>

Komponen anak dapat menerima data tersebut menggunakan defineProps().

Sebelum Vue 3.5, developer perlu memahami bahwa melakukan destructuring terhadap props dapat membuat nilai primitive kehilangan hubungan reaktivitasnya.

Masalah Destructuring Sebelum Vue 3.5

Contoh pola lama:

<script setup>
const props = defineProps({
  count: Number,
  msg: String
})

const { count, msg } = props
</script>

Pada JavaScript biasa, destructuring tersebut mengambil nilai property ke variabel lokal.

Konsep ini berbeda dengan mengakses:

props.count

Karena Vue melakukan tracking berdasarkan akses terhadap property reactive object.

Dokumentasi Vue menjelaskan bahwa secara umum destructuring property primitive dari reactive object dapat memutus hubungan reaktivitas.

Karena itu, developer biasanya menggunakan props.count, toRefs(), atau pola lain untuk mempertahankan hubungan reaktif.

Cara Baru di Vue 3.5

Vue 3.5 membuat destructuring langsung dari defineProps() menjadi reactive di dalam <script setup>.

Contohnya:

<script setup>
const { count, msg } = defineProps({
  count: Number,
  msg: String
})
</script>

<template>
  <p>{{ count }}</p>
  <p>{{ msg }}</p>
</template>

Vue compiler secara otomatis menangani akses terhadap variable hasil destructuring tersebut. Secara konsep, ketika kode menggunakan count, compiler dapat memperlakukannya seperti akses terhadap props.count.

Inilah alasan fitur tersebut disebut Reactive Props Destructure.

Default Value Lebih Sederhana

Salah satu keuntungan terbesar lainnya adalah penentuan default value.

Pada Vue 3.5, developer dapat menggunakan sintaks default assignment JavaScript:

<script setup>
const {
  msg = 'Halo Dunia!',
  count = 0
} = defineProps({
  msg: String,
  count: Number
})
</script>

Dengan pola tersebut, kode menjadi lebih ringkas.

Jika menggunakan TypeScript:

<script setup lang="ts">
interface Props {
  msg?: string
  count?: number
}

const {
  msg = 'Halo Dunia!',
  count = 0
} = defineProps<Props>()
</script>

Vue mendukung pola default value tersebut pada Reactive Props Destructure.

Bagaimana dengan withDefaults?

Sebelum Vue 3.5, ketika menggunakan type-based props declaration, developer sering menggunakan withDefaults() untuk memberikan nilai default.

Contohnya:

<script setup lang="ts">
interface Props {
  msg?: string
  labels?: string[]
}

const props = withDefaults(defineProps<Props>(), {
  msg: 'Hello',
  labels: () => ['One', 'Two']
})
</script>

Di Vue 3.5, destructuring dapat digunakan:

<script setup lang="ts">
interface Props {
  msg?: string
  labels?: string[]
}

const {
  msg = 'Hello',
  labels = ['One', 'Two']
} = defineProps<Props>()
</script>

Namun, withDefaults() bukan berarti langsung tidak berguna. Kode lama yang menggunakan withDefaults() tetap relevan dan tidak perlu dihapus hanya karena Vue 3.5 sudah menyediakan Reactive Props Destructure.

Hal Penting Saat Menggunakan Reactive Props Destructure

Meskipun fitur ini membuat kode lebih sederhana, ada satu hal penting yang perlu dipahami.

Misalnya:

<script setup>
const { count } = defineProps(['count'])

watch(count, () => {
  console.log('changed')
})
</script>

Pola tersebut tidak tepat untuk mempertahankan reactive source karena watch() menerima nilai, bukan getter.

Vue merekomendasikan menggunakan getter:

<script setup>
const { count } = defineProps(['count'])

watch(() => count, () => {
  console.log('changed')
})
</script>

Pola yang sama berlaku ketika props destructured diberikan kepada composable yang membutuhkan reactive source.

Jadi, Reactive Props Destructure memang membuat kode lebih bersih, tetapi developer tetap perlu memahami kapan sebuah nilai harus diberikan sebagai getter.

Watcher Improvements di Vue 3.5

Selain props, watcher juga mendapatkan sejumlah peningkatan yang berguna untuk aplikasi yang menangani data dinamis.

Watcher digunakan ketika developer ingin menjalankan sebuah fungsi setelah reactive data mengalami perubahan.

Contohnya:

<script setup>
import { ref, watch } from 'vue'

const search = ref('')

watch(search, (newValue) => {
  console.log('Search:', newValue)
})
</script>

Vue 3.5 memperkenalkan onWatcherCleanup() sebagai API untuk mendaftarkan fungsi cleanup dari watcher.

Apa Itu onWatcherCleanup?

Bayangkan sebuah aplikasi melakukan request API berdasarkan input pencarian.

User mengetik:

Laptop

Kemudian request dikirim.

Sebelum request selesai, user mengganti menjadi:

Laptop Lenovo

Request kedua dikirim.

Jika request pertama belum selesai, aplikasi dapat mengalami kondisi di mana response lama datang setelah response baru.

Cleanup dapat digunakan untuk membatalkan pekerjaan yang sudah tidak relevan.

Contohnya:

<script setup>
import {
  watch,
  onWatcherCleanup
} from 'vue'

watch(search, async (value) => {
  const controller = new AbortController()

  onWatcherCleanup(() => {
    controller.abort()
  })

  await fetch(`/api/search?q=${value}`, {
    signal: controller.signal
  })
})
</script>

Ketika watcher dijalankan kembali, cleanup dari proses sebelumnya dapat dipanggil sehingga pekerjaan lama bisa dihentikan.

Bagi aplikasi yang banyak melakukan asynchronous operation, fitur ini membantu membuat pengelolaan side effect menjadi lebih terstruktur.

Deep Watcher Lebih Fleksibel

Vue 3.5 juga memperkenalkan kemampuan menggunakan angka pada opsi deep untuk menentukan kedalaman traversal watcher.

Sebelumnya, developer dapat menggunakan:

watch(source, callback, {
  deep: true
})

Masalahnya, deep: true dapat membuat Vue melakukan traversal hingga struktur yang sangat dalam.

Pada Vue 3.5, developer dapat menggunakan:

watch(source, callback, {
  deep: 1
})

Ini berguna ketika developer hanya ingin mengamati perubahan sampai tingkat tertentu.

Dokumentasi Vue menjelaskan bahwa pada Vue 3.5+, deep dapat berupa angka yang menentukan maksimum kedalaman traversal.

Perubahan Watch Array

Developer yang melakukan upgrade juga perlu memperhatikan perilaku watcher terhadap array.

Pada Vue 3.5, ketika sebuah array di-watch, callback tidak otomatis dijalankan hanya karena terjadi mutation pada array. Jika ingin mengamati penggantian array sekaligus mutation pada array, Vue menyediakan deep: 1.

Contohnya:

watch(
  bookList,
  () => {
    console.log('Book list changed')
  },
  {
    deep: 1
  }
)

Ini menjadi salah satu area yang perlu diperiksa ketika melakukan upgrade pada aplikasi yang sudah menggunakan watcher untuk array.

useTemplateRef() untuk Referensi DOM

Vue 3.5 juga memperkenalkan useTemplateRef().

Sebelumnya, developer biasanya membuat:

<script setup>
import { ref, onMounted } from 'vue'

const input = ref(null)

onMounted(() => {
  input.value.focus()
})
</script>

<template>
  <input ref="input">
</template>

Pada Vue 3.5, pola tersebut dapat ditulis menggunakan:

<script setup>
import { useTemplateRef, onMounted } from 'vue'

const input = useTemplateRef('input')

onMounted(() => {
  input.value.focus()
})
</script>

<template>
  <input ref="input">
</template>

useTemplateRef() membuat hubungan antara template reference dan kode <script setup> menjadi lebih eksplisit. Dukungan tooling Vue juga membantu memberikan informasi tipe berdasarkan template ref yang digunakan.

Fitur ini sangat berguna untuk komponen yang berinteraksi langsung dengan DOM, seperti:

  • input autofocus
  • video player
  • canvas
  • elemen dengan animasi
  • integrasi library JavaScript
  • pengukuran ukuran elemen

useId() untuk ID yang Aman pada SSR

Vue 3.5 juga memperkenalkan useId().

API ini dirancang untuk menghasilkan ID unik yang konsisten dan aman digunakan dalam aplikasi yang memakai SSR atau Server-Side Rendering.

SSR adalah teknik ketika HTML awal halaman dibuat di server kemudian dikirim ke browser. Setelah itu Vue melakukan hydration agar HTML tersebut menjadi interaktif.

ID yang berbeda antara server dan client dapat menyebabkan masalah hydration.

Dengan useId(), developer dapat menghasilkan ID yang cocok digunakan untuk kebutuhan seperti accessibility.

Contohnya:

<script setup>
import { useId } from 'vue'

const id = useId()
</script>

<template>
  <label :for="id">
    Nama
  </label>

  <input :id="id">
</template>

Pola ini sangat berguna ketika membuat komponen reusable yang memiliki hubungan antara <label> dan <input>, atau ketika membutuhkan aria-describedby dan atribut accessibility lainnya.

Deferred Teleport

<Teleport> merupakan fitur Vue untuk merender bagian template ke lokasi DOM lain.

Contoh yang umum adalah modal:

<Teleport to="body">
  <div class="modal">
    ...
  </div>
</Teleport>

Sebelumnya, target <Teleport> perlu tersedia ketika komponen dipasang.

Vue 3.5 memperkenalkan atribut defer sehingga target dapat tersedia pada tahap render yang lebih belakangan dalam siklus render yang sama.

Contohnya:

<Teleport defer to="#container">
  <div>
    Konten
  </div>
</Teleport>

<div id="container"></div>

Fitur ini membuat penggunaan Teleport menjadi lebih fleksibel ketika target juga dihasilkan oleh Vue.

Lazy Hydration untuk Aplikasi SSR

Vue 3.5 juga membawa peningkatan pada hydration untuk async component.

Hydration adalah proses ketika Vue mengambil HTML yang sudah dibuat sebelumnya, misalnya dari server, kemudian menghubungkannya dengan JavaScript agar menjadi interaktif.

Pada aplikasi besar, tidak semua komponen harus langsung aktif ketika halaman pertama kali dibuka.

Komponen tertentu mungkin berada jauh di bawah halaman dan belum terlihat oleh pengguna. Mengaktifkan semuanya sekaligus dapat menambah pekerjaan browser.

Vue 3.5 menyediakan strategi lazy hydration untuk async components sehingga hydration dapat ditunda berdasarkan kondisi tertentu, seperti ketika elemen terlihat atau browser berada dalam kondisi idle.

Pendekatan ini dapat membantu aplikasi SSR mengurangi pekerjaan awal di browser, khususnya pada halaman yang memiliki banyak komponen interaktif.

Dampak Vue 3.5 terhadap Developer Experience

Salah satu kelebihan Vue 3.5 adalah peningkatan yang tidak hanya berhubungan dengan benchmark.

Reactive Props Destructure membuat kode lebih dekat dengan sintaks JavaScript standar.

Sebelumnya:

const props = defineProps()
const count = toRef(props, 'count')

Sekarang developer dapat menulis:

const { count } = defineProps()

Dengan catatan, ketika nilai tersebut digunakan sebagai reactive source untuk watch() atau composable, gunakan getter jika diperlukan:

watch(() => count, callback)

Perubahan seperti ini terlihat kecil, tetapi pada proyek dengan ratusan komponen, pengurangan boilerplate dapat memberikan efek positif terhadap keterbacaan dan pemeliharaan kode.

Apakah Vue 3.5 Cocok untuk Aplikasi Skala Besar?

Vue 3.5 sangat relevan untuk aplikasi yang mempunyai reactive state dalam jumlah besar.

Contohnya:

Dashboard Enterprise

Dashboard biasanya mempunyai banyak widget, tabel, filter, grafik, dan data realtime.

Semakin banyak data yang reaktif, semakin penting efisiensi dependency tracking.

E-commerce

E-commerce dapat mempunyai:

  • ribuan produk
  • filter dinamis
  • keranjang
  • wishlist
  • rekomendasi
  • variasi produk
  • data harga
  • stok realtime

Optimasi reaktivitas dan array dapat membantu pada bagian aplikasi yang mempunyai struktur data kompleks.

SaaS

Aplikasi SaaS biasanya menggunakan banyak komponen form, tabel, modal, notification, dan state global.

Fitur seperti Reactive Props Destructure dan onWatcherCleanup() dapat membuat kode lebih mudah dikelola.

Aplikasi SSR

Aplikasi yang menggunakan SSR mendapatkan manfaat dari useId(), peningkatan hydration, dan perbaikan internal pada reaktivitas.

Framework seperti Nuxt yang dibangun di atas Vue juga dapat memperoleh manfaat dari peningkatan yang berada pada core Vue, walaupun hasil aktual tetap bergantung pada arsitektur aplikasi.

Apakah Upgrade ke Vue 3.5 Membutuhkan Perubahan Besar?

Vue 3.5 diposisikan sebagai minor release dan pengumuman resminya menyatakan tidak ada breaking changes umum pada rilis tersebut.

Namun, tidak adanya breaking changes bukan berarti upgrade boleh dilakukan tanpa pengujian.

Developer tetap perlu memeriksa bagian aplikasi yang berhubungan dengan watcher, terutama jika aplikasi menggunakan watcher array atau pola reaktivitas tertentu.

Untuk proyek yang menggunakan Reactive Props Destructure versi eksperimental sebelumnya, konfigurasi lama juga sebaiknya diperiksa agar sesuai dengan perilaku Vue 3.5.

Cara Upgrade ke Vue 3.5

Untuk proyek yang sudah menggunakan Vue 3, salah satu pendekatan adalah memperbarui dependency Vue melalui package manager.

Contohnya:

npm install [email protected]

Jika ingin menggunakan versi terbaru yang tersedia dalam major release yang sesuai, perintah yang umum digunakan adalah:

npm install vue@latest

Perintah:

npm update vue

juga dapat digunakan, tetapi perlu dipahami bahwa npm update mengikuti batas versi yang ditentukan oleh package.json. Jadi, hasilnya bergantung pada version range yang digunakan proyek.

Setelah upgrade, jalankan kembali:

npm install
npm run build

Kemudian lakukan pengujian aplikasi, terutama pada:

  • component rendering
  • watcher
  • computed
  • form
  • dynamic component
  • SSR atau hydration
  • array reactive
  • asynchronous request
  • template refs

Apa yang Perlu Diperiksa Setelah Upgrade?

Ada beberapa bagian yang sebaiknya diperiksa sebelum aplikasi Vue 3.5 digunakan di production.

Pertama, periksa watcher terhadap array. Jika aplikasi bergantung pada mutation array, pertimbangkan penggunaan deep: 1 sesuai kebutuhan.

Kedua, periksa penggunaan Reactive Props Destructure. Jika sebuah destructured prop diberikan langsung ke watch(), ubah menjadi getter:

watch(() => count, callback)

Ketiga, periksa kode SSR jika aplikasi menggunakan server-side rendering.

Keempat, jalankan automated test dan build production.

Kelima, lakukan pengukuran performa pada aplikasi sendiri. Angka benchmark 56% pengurangan memori dan hingga 10 kali peningkatan performa array bukan berarti setiap aplikasi akan mendapatkan angka yang sama.

Hasil sebenarnya tergantung jumlah reactive state, ukuran data, struktur komponen, penggunaan watcher, browser, bundler, SSR, dan arsitektur aplikasi.

Vue 3.5 Lebih dari Sekadar Update Performa

Jika hanya melihat daftar API baru, Vue 3.5 mungkin terlihat seperti update kecil.

Namun, perubahan terbesar justru berada di bagian internal.

Refactor reactivity system memberikan fondasi yang lebih efisien. Reactive Props Destructure mengurangi boilerplate. onWatcherCleanup() membuat pengelolaan asynchronous side effect lebih rapi. useTemplateRef() menyederhanakan akses template ref. useId() membantu kebutuhan SSR dan accessibility.

Ditambah optimasi array, Deferred Teleport, dan peningkatan lazy hydration, Vue 3.5 menjadi rilis yang cukup lengkap dari sisi performa sekaligus developer experience.

Bagi developer yang sudah menggunakan Vue 3, fitur baru ini juga tidak mengharuskan seluruh kode ditulis ulang. Banyak manfaat dapat diperoleh secara bertahap ketika komponen lama mulai direfactor.

Perbandingan Vue 3.4 dan Vue 3.5

AspekVue 3.4Vue 3.5
Reactive Props DestructureBelum aktif secara defaultStabil dan aktif secara default
Destructuring defineProps()Perlu perhatian terhadap reaktivitasTetap reactive dalam <script setup>
Default propsDapat menggunakan withDefaults()Dapat menggunakan default assignment JavaScript
Sistem reaktivitasSistem sebelumnyaRefactor internal dengan dependency tracking yang lebih efisien
Penggunaan memori reactivityBaseline sebelumnyaHingga 56% lebih rendah pada benchmark tertentu
Array reaktif besarSistem sebelumnyaOptimasi tracking, hingga 10x lebih cepat pada kasus tertentu
onWatcherCleanup()Belum tersediaTersedia
Numeric deep watcherBelum tersediaTersedia, misalnya deep: 1
useTemplateRef()Belum tersediaTersedia
useId()Belum tersediaTersedia
Deferred TeleportBelum tersediaMendukung defer
Lazy hydrationLebih terbatasStrategi hydration untuk async component ditingkatkan
SSRDukungan Vue 3Mendapat sejumlah peningkatan
Breaking changes dari 3.4–Tidak ada breaking changes umum dalam minor release
Fokus utamaStabilitas dan fitur Vue 3Performa, efisiensi memori, SSR, dan developer experience

Jadi, Apa Arti Vue 3.5 bagi Developer?

Vue 3.5 menunjukkan bahwa peningkatan framework tidak selalu harus hadir dalam bentuk API yang besar.

Perubahan internal seperti optimasi dependency tracking mungkin tidak terlihat langsung di kode, tetapi dapat memberikan dampak ketika aplikasi semakin besar.

Sementara itu, Reactive Props Destructure merupakan perubahan yang jauh lebih terlihat. Developer dapat menulis komponen dengan syntax yang lebih sederhana tanpa harus kehilangan reaktivitas pada destructured props.

Contohnya:

<script setup lang="ts">

interface Props {
  title?: string
  count?: number
}

const {
  title = 'Dashboard',
  count = 0
} = defineProps<Props>()

</script>

<template>
  <section>
    <h2>{{ title }}</h2>
    <p>Total: {{ count }}</p>
  </section>
</template>

Kode tersebut terasa lebih natural karena menggunakan kemampuan destructuring JavaScript yang sudah dikenal banyak developer.

Di sisi performa, developer tidak perlu melakukan optimasi manual hanya untuk mendapatkan keuntungan dari refactor reactivity system. Core Vue yang baru menangani banyak pekerjaan tersebut di belakang layar.

Dengan demikian, Vue 3.5 dapat dilihat sebagai kombinasi antara optimasi internal dan peningkatan ergonomi API. Untuk aplikasi sederhana, perubahannya mungkin tidak langsung terasa. Tetapi pada aplikasi besar dengan banyak reactive state, array kompleks, watcher, SSR, dan komponen dinamis, manfaatnya menjadi jauh lebih relevan.

Secara keseluruhan, Vue 3.5 merupakan salah satu rilis penting dalam evolusi Vue 3, terutama karena peningkatan performanya dilakukan tanpa mengubah pola dasar pengembangan Vue secara drastis. Developer dapat tetap menggunakan ref(), reactive(), computed(), watch(), Composition API, dan <script setup> seperti biasa, sambil mendapatkan sistem internal yang lebih efisien.

Untuk proyek baru, fitur seperti Reactive Props Destructure, useTemplateRef(), useId(), dan onWatcherCleanup() dapat langsung dipertimbangkan. Untuk proyek lama, upgrade sebaiknya dilakukan secara bertahap dengan pengujian watcher, SSR, dan komponen yang mempunyai reactive state kompleks.

Dokumentasi resmi Vue tetap menjadi rujukan utama untuk detail API, terutama karena beberapa perilaku seperti watch(), Reactive Props Destructure, dan deep watcher memiliki aturan penggunaan yang spesifik.

Facebook
Twitter
LinkedIn