JAVASCRIPT

Reusable Data Fetching Composable in Vue 3

Create a custom composable function in Vue 3 to encapsulate data fetching logic, making it reusable, reactive, and easy to integrate into any component that needs to fetch data.

// useFetch.js
import { ref, onMounted, toValue } from 'vue';

export function useFetch(url) {
  const data = ref(null);
  const error = ref(null);
  const loading = ref(true);

  async function fetchData() {
    loading.value = true;
    error.value = null;
    data.value = null;
    try {
      // toValue ensures that if url is a ref, its value is extracted
      const res = await fetch(toValue(url));
      if (!res.ok) {
        throw new Error(`HTTP error! status: ${res.status}`);
      }
      data.value = await res.json();
    } catch (e) {
      error.value = e;
    } finally {
      loading.value = false;
    }
  }

  // Fetch data on component mount by default
  onMounted(() => fetchData());

  return { data, error, loading, fetchData };
}

<!-- ComponentUsingFetch.vue -->
<template>
  <div>
    <h1>Data from API</h1>
    <p v-if="loading">Loading...</p>
    <p v-else-if="error">Error: {{ error.message }}</p>
    <pre v-else>{{ data }}</pre>
    <button @click="fetchData">Refresh Data</button>
  </div>
</template>

<script setup>
import { useFetch } from './useFetch'; // Assuming useFetch.js is in the same directory

const { data, error, loading, fetchData } = useFetch('https://jsonplaceholder.typicode.com/todos/1');

// Example of using a reactive URL:
// import { ref, watch } from 'vue';
// const userId = ref(1);
// const { data, error, loading } = useFetch(() => `https://jsonplaceholder.typicode.com/users/${userId.value}`);
// watch(userId, () => { /* data will automatically refetch if the composable watches its arguments, 
// which it does here by using toValue on url argument inside fetchData. */ });
</script>
How it works: This snippet provides a reusable data fetching composable (`useFetch`) for Vue 3. Composables are functions that encapsulate stateful logic and can be reused across components, promoting better organization and reusability. The `useFetch` composable handles the loading state, potential errors, and the fetched data itself, exposing them as reactive `ref`s. It automatically fetches data when the component mounts and includes a `fetchData` function for manual refresh. Using `toValue(url)` allows the URL parameter to be either a static string or a reactive `ref`, enabling dynamic API calls.

Need help integrating this into your project?

Our team of expert developers can help you build your custom application from scratch.

Hire DigitalCodeLabs