Question presented to candidate:
"We have a legacy component that pulls in four mixins, and nobody is sure where count or reset() comes from. Why does the Vue team recommend composables over mixins, and how would you refactor this?"
What a strong answer should cover:
- Mixins merge options into the component, so their data and methods appear on
thiswith no trace of where they came from. - Name collisions are silent: for
dataandmethods, a later mixin overwrites an earlier one and the component overrides both, with no warning. - Implicit dependencies: a mixin can read
this.somethingthat it expects the component (or another mixin) to define. - The
datamerge is shallow in Vue 3, and lifecycle hooks from all mixins run (mixins first). - Composables fix each problem: explicit imports, renaming on destructure, dependencies passed as arguments, and types that infer.
- Mixins still work in Vue 3, and global mixins (
app.mixin) are worse because they touch every component, including third-party ones.
Clarifying questions expected:
- "Are any of these mixins global, or only local to this component?"
- "Do other components depend on the same mixins? That decides whether to extract shared composables first."
Code / implementation expected: Yes β a reproduction of a mixin name collision and the composable rewrite that removes it.