📖 Scenario: You are building a Vue 3 app that needs to fetch user data from an API. To keep your code clean and reusable, you want to create a composable function that handles fetching data and managing loading and error states.
🎯 Goal: Create a Vue 3 composable called useFetch that fetches data from a given URL and provides reactive data, loading, and error states.
📋 What You'll Learn
Use Vue 3 Composition API with ref and watchEffect
Create a composable function useFetch that accepts a URL string
Manage reactive variables data, loading, and error
Fetch data automatically when the URL changes
Return the reactive variables from the composable
💡 Why This Matters
🌍 Real World
Creating reusable composable functions for API calls helps keep Vue apps clean and maintainable. It allows multiple components to share fetching logic easily.
💼 Career
Understanding composables and reactive data fetching is essential for modern Vue development roles, improving code reuse and user experience.
Progress0 / 4 steps
1
Setup reactive variables
In a new file, create a composable function called useFetch. Inside it, create three reactive variables using ref: data initialized to null, loading initialized to false, and error initialized to null.
Vue
Hint
Use ref from Vue to create reactive variables inside your composable.
2
Add watchEffect to fetch data
Import watchEffect from 'vue'. Inside useFetch, add a watchEffect that runs whenever url changes. Inside it, set loading to true, reset error to null, then fetch the data from url. On success, set data.value to the JSON response. On failure, set error.value to the error message. Finally, set loading to false.
Vue
Hint
Use watchEffect to reactively run the fetch code when url changes.
3
Return reactive variables
At the end of the useFetch function, return an object containing the reactive variables data, loading, and error.
Vue
Hint
Return an object with the reactive variables so components can use them.
4
Use the composable in a component
Create a Vue component that imports useFetch. Inside the setup function, call useFetch with the URL https://jsonplaceholder.typicode.com/users. Return the reactive variables data, loading, and error from setup. In the template, show a loading message when loading is true, an error message when error is not null, and a list of user names when data is available.
Vue
Hint
Use the composable inside setup and bind the reactive variables in the template with Vue directives.
Practice
(1/5)
1. What is the main purpose of a composable like useFetch in Vue?
easy
A. To fetch data from an API and manage loading and error states reactively
B. To style components with CSS variables
C. To create Vue directives for DOM manipulation
D. To define routes in a Vue application
Solution
Step 1: Understand composable role
A composable in Vue is a reusable function that encapsulates logic, often for state or side effects.
Step 2: Identify useFetch purpose
The useFetch composable specifically handles API calls and manages reactive states like loading and error.
Final Answer:
To fetch data from an API and manage loading and error states reactively -> Option A
Quick Check:
Composable useFetch = fetch + reactive states [OK]
Hint: Composable useFetch manages API data and states reactively [OK]
Common Mistakes:
Confusing composables with styling or routing
Thinking composables only handle UI rendering
Assuming composables are Vue components
2. Which of the following is the correct way to import and use a useFetch composable in a Vue component?
easy
A. const { useFetch } = Vue; const result = useFetch(url);
B. import useFetch from 'vue'; const data = useFetch(url);
C. import { useFetch } from '@/composables/useFetch'; const { data, error } = useFetch(url);
D. import { fetchData } from '@/composables'; fetchData(url);
Solution
Step 1: Check import syntax
The composable is usually exported from a file and imported with curly braces if it's a named export.
Step 2: Using the composable
Calling useFetch(url) returns reactive properties like data and error.
Final Answer:
import { useFetch } from '@/composables/useFetch'; const { data, error } = useFetch(url); -> Option C
A. Setting loading.value = true after fetch call starts causes race condition
B. Not using async/await causes syntax error
C. data should be initialized as an empty array, not null
D. Error ref should be initialized as an empty string
Solution
Step 1: Analyze loading state timing
Loading is set to false inside fetch callbacks but set to true after fetch starts, which can cause timing issues.
Step 2: Identify race condition
Because loading is set to true after fetch call, it might overwrite loading false set in callbacks if fetch resolves quickly.
Final Answer:
Setting loading.value = true after fetch call starts causes race condition -> Option A
Quick Check:
Loading state timing error = Setting loading.value = true after fetch call starts causes race condition [OK]
Hint: Set loading true before fetch call to avoid race [OK]
Common Mistakes:
Setting loading true after fetch call instead of before
Confusing async/await with promises syntax errors
Assuming initial data type must be array
5. You want to create a useFetch composable that automatically retries fetching up to 3 times if the API call fails. Which approach correctly adds this retry logic?
hard
A. Wrap fetch in a try/catch but do not retry on failure
B. Call fetch once and ignore errors, relying on component to retry
C. Use setTimeout outside the composable to call useFetch repeatedly
D. Use a recursive function inside the composable that calls fetch again on error until max retries reached