Vue 3
Vue 3 builds user interfaces from components whose state is reactive: change the data and the view follows, with no explicit update call. It is the frontend framework in every web project in this garden, and the reason is less about capability than about how much ceremony ordinary tasks require.
What the Composition API changed
Vue 2’s Options API organised a component by kind of thing — all data here, all methods there, all computed values below. That reads well for a small component and scatters any single feature across four sections in a large one. Extracting shared logic meant mixins, which merge invisibly and collide silently.
The Composition API organises by feature instead. Related state, computed values, and functions sit together in setup, and extracting them into a composable is moving code into a function that returns what it exposes. Nothing implicit, nothing merged, and it composes.
That is the real improvement. Not new capability, but shared logic becoming a plain function rather than a framework mechanism.
The reactivity trap
Vue’s reactivity works through proxies, which means it tracks property access on an object. Destructuring a reactive object copies values and drops the connection, so const { count } = store gives a number that will never update — with no error, just a component that silently stops re-rendering.
storeToRefs and toRefs exist for this. It is the single most common Vue bug I have written, and the one to internalise before anything else.
The corresponding rule with ref is that .value is required in script and not in template, which reads as inconsistent until the reason is clear: the template unwraps refs automatically. Knowing that makes it predictable rather than arbitrary.
Why I keep choosing it
Single-file components put template, script, and scoped styles in one file, and having styles scoped by default removes a whole category of CSS problem without a naming convention. TypeScript support with <script setup lang="ts"> is good enough that props and emits are properly typed.
The honest comparison against React is that the ecosystem is smaller, so there are fewer libraries and fewer answers to unusual problems. In exchange, the official libraries — Pinia for state, Vue Router — are actually official, which means one obvious choice rather than a decision to research. For a small team that is worth more than ecosystem breadth.
See also: Pinia, Vite, Vuetify, Nuxt 3, and Status Alganize for the pattern in use.