Hey!
I hope you're enjoying your summer (or winter!).
Now that Mastering Nuxt: Full Stack Unleashed is finally complete, I've started working on my next course: Advanced Reactivity in Vue
It will cover aspects of watchers, computed, refs, and deeper parts of Vue's reactivity system you probably have never worked with before. I'll share progress updates as I work on it!
Since Mastering Nuxt is now finished, the early access discount will be expiring at the end of July! So you have just about a week to grab it before the price goes up.
This week I've been re-recording some lessons and making sure it's fully up-to-date, a few things (like Nuxt 4) have changed since I did the recordings.
We plan to keep this always up-to-date going forward. We'll also be creating new courses on other Nuxt topics so you can deepen your Nuxt learning even more.
Go here to get Mastering Nuxt before the price goes up: Mastering Nuxt: Full Stack Unleashed
— Michael
If you have multiple levels of nested slots, it's possible to have defaults at each level:
<!-- Parent.vue --><template><Child><slot>We're in the Parent!</slot></Child></template>
<!-- Child.vue --><template><div><slot>We're in the Child!</slot></div></template>
The slot content provided at the highest point in the hierarchy will override everything below it.
If we render Parent, it will always display We're in the Parent. But if we render just the Child component, we get We're in the Child!.
And if the component rendering the Parent component provides slot content, that will take precedence over everything:
<!-- Grandparent.vue --><template><Parent>Haha this content rules them all!</Parent></template>
Let's take a slot and split it into two slots:
<!-- Parent.vue --><template><Child><!-- Splitting a slot into multiple requiresa conditional. This allows you to branchinto however many slots you want --><slot v-if="left" name="left" /><slot v-else name="right" /></Child></template>
Our Child component only accepts one slot, but the Parent component accepts two.
Here, the Parent component switches between which slot it uses based on the value of left.
We can also use default slot content, if one or both of the Parent slots have no content:
<!-- Parent.vue --><template><Child><slot v-if="left" name="left"><!-- Default content works like you'd expect --><div key="left">Default left</div></slot><slot v-else name="right"><div key="right">Default Right</div></slot></Child></template>
When you register a component globally, you can use it in any template without importing it a second time:
// Vue 3import { createApp } from 'vue';import GlobalComponent from './GlobalComponent.vue';const app = createApp({})app.component('GlobalComponent', GlobalComponent);
In Vue 2 you can register global components like this:
// Vue 2import Vue from 'vue';import GlobalComponent from './GlobalComponent.vue';Vue.component('GlobalComponent', GlobalComponent);
Now you can use GlobalComponent in your templates without any extra work!
Of course, globally registered components have the same pros and cons as global variables. So use this sparingly.
No new episode this week, but here are the latest episodes of DejaVue:
Unit testing is a crucial part of building robust applications.
In this article I explore how to unit test your Nuxt applications using the Nuxt Test Utils.
Check it out here: Unit Testing in Nuxt
An extremely common question I get asked all the time is, “how do you know when to split up a component?”
I want to share a simple pattern with you that is basically fool-proof, and can be applied to lots of components with almost no thought.
Check it out here: The Extract Conditional Pattern in Vue
"Testing can only prove the presence of bugs, not their absence." — Edsger W. Dijkstra
The best way to commit something to long-term memory is to periodically review it, gradually increasing the time between reviews 👨‍🔬
Actually remembering these tips is much more useful than just a quick distraction, so here's a tip from a couple weeks ago to jog your memory.
You may not have known this, but you can easily watch nested values directly when using the Options API, just by using quotes:
watch: {'$route.query.id'() {// ...}}
This is really useful for working with deeply nested objects!
We can also watch nested values using the Composition API:
watch(() => value.that.is.really.nested,() => {// ...});
Michael Hoffman curates a fantastic weekly newsletter with the best Vue and Nuxt links.
p.s. I also have a bunch of products/courses: