Provide / Inject

Dependency Injection

Provide and Inject enable dependency injection in Vue. They solve the problem of "props drilling" - passing props through many levels of components just to reach a deeply nested child.

With provide/inject, a parent component can serve as a dependency provider for all its descendants, regardless of how deep the component hierarchy is.

How It Works

A parent component uses provide() to make data available:

<script setup>
const theme = ref('dark')
provide('theme', theme)
</script>

Any descendant component can use inject() to receive that data:

<script setup>
const theme = inject('theme')
</script>

When to Use Provide/Inject

Use provide/inject when:

  • You have deeply nested components that need access to the same data
  • Building reusable component libraries (like theme systems)
  • Sharing global state that doesn't change often

Avoid provide/inject when:

  • You only need to pass data one level down (use props instead)
  • You need complex state management (use Pinia instead)
  • The data changes frequently and you need fine-grained reactivity tracking

Reactive Injection

To make injected values reactive, provide a ref or reactive object:

<script setup>
// Provider
const theme = ref('dark')
provide('theme', theme)

function toggleTheme() {
  theme.value = theme.value === 'dark' ? 'light' : 'dark'
}
provide('toggleTheme', toggleTheme)
</script>
<script setup>
// Consumer
const theme = inject('theme')
const toggleTheme = inject('toggleTheme')
</script>

Challenge

Create a theme system using provide/inject:

  1. In app.vue, create a ThemeProvider component that:
    • Provides a reactive theme ref (values: 'light' or 'dark')
    • Provides a toggleTheme function
    • Wraps the ThemedButton components
  2. Create a ThemedButton component that:
    • Injects the theme value
    • Injects the toggleTheme function
    • Changes its appearance based on the theme
    • Toggles the theme when clicked
  3. Create multiple ThemedButton components to show they all share the same theme

Tip: Use provide('key', value) in the parent and inject('key') in descendants. Make sure to provide a ref for reactivity.

If you get stuck, you can check the solution by clicking the button below.


Provide/inject is powerful for building flexible component systems, but remember: for most cases, props are clearer and easier to debug. Use provide/inject when props drilling becomes unwieldy.

Slots
Vue Basics Summary
Great! You've learned the basics of Vue. If you are interested in learning more about Vue, check out the official Vue documentation for more in-depth guides and tutorials.
Files
Editor
Initializing WebContainer
Mounting files
Installing dependencies
Starting Nuxt server
Waiting for Nuxt to ready
Terminal