重複使用的方法
自己包一個可重複使用的 Fetch
方法 1: 回傳 Promise
- 新增 fetch.js Promise
js
export function fetchAct(url) {
return new Promise((resolve, reject) => {
const status = statusStore();
status.isLoading = true;
axios
.get(url)
.then((response) => {
status.isLoading = false;
if (response.data.success) {
resolve(response.data);
} else {
reject(new Error("Fetch failed: " + response.data.message));
}
})
.catch((error) => {
status.isLoading = false;
catchErr(error);
reject(error);
});
});
}
- pinia getOrders 修改
- 用 async /await 寫法
js
async function getOrders(currentPage = 1) {
// 使用 async
pagination.value.currentPage = currentPage;
const url = `${userOrdersApi}?page=${currentPage}`;
try {
const data = await fetchAct(url); // 使用 await 等待异步操作完成
orders.value = data.orders;
pagination.value = data.pagination;
} catch (error) {
console.error("Failed to fetch orders:", error);
}
}
- 不用 async /await 寫法
js
function getOrders(currentPage = 1) {
pagination.value.currentPage = currentPage;
const url = `${userOrdersApi}?page=${currentPage}`;
fetchAct(url).then((data) => {
orders.value = data.orders;
pagination.value = data.pagination;
});
}
方法 2: 組合式函數?
- [ ] 待確認使用方式
js
export function useFetch(url) {
const data = ref(null);
const error = ref(null);
const status = statusStore();
status.isLoading = true;
// fetch(url)
// .then((res) => res.json())
// .then((json) => (data.value = json))
// .catch((err) => (error.value = err))
axios
.get(url)
.then((response) => {
status.isLoading = false;
//data.value = response.data
//success??
if (response.data.success) {
data.value = response.data;
console.log("response data", data.value);
} else {
dataErr(response);
}
})
.catch((err) => {
status.isLoading = false;
catchErr(err);
error.value = err;
});
return { data, error };
}
- pinia
js
function getOrders(currentPage = 1) {
pagination.value.currentPage = currentPage;
const url = `${userOrdersApi}?page=${currentPage}`;
const { data, error } = useFetch(url); //寫在這邊似乎有點奇怪 看範例都是定義在外部
// if (data.value) {//因為是非同步所以這邊會抓到 null 還要搭配 watchEffect 去抓取
// orders.value = data.value.orders;
// pagination.value = data.value.pagination;
// }
watchEffect(() => {
if (data.value) {
orders.value = data.value.orders;
pagination.value = data.value.pagination;
}
if (error.value) {
console.error("Failed to fetch orders:", error.value);
}
});
}
再看一次範例
js
import { defineStore, skipHydrate } from 'pinia'
import { useMediaControls } from '@vueuse/core'
export const useVideoPlayer = defineStore('video', () => {
// 我们不会直接暴露这个元素
const videoElement = ref<HTMLVideoElement>()
const src = ref('/data/video.mp4')
const { playing, volume, currentTime, togglePictureInPicture } =
useMediaControls(video, { src })
function loadVideo(element: HTMLVideoElement, src: string) {
videoElement.value = element
src.value = src
}
return {
src,
playing,
volume,
currentTime,
loadVideo,
togglePictureInPicture,
}
})
這是在組件中直接用
js
<script setup>
import { ref, computed } from 'vue'
import { useFetch } from './useFetch.js'
const baseUrl = 'https://jsonplaceholder.typicode.com/todos/'
const id = ref('1')
const url = computed(() => baseUrl + id.value)
const { data, error } = useFetch(url)
const retry = () => {
id.value = ''
id.value = '1'
}
</script>
fetchAct
我想用創建自己一個類似 axios 的 叫做 fetchAct 他導入時 自己就是實例化
要实现类似 axios 的 fetchAct,并且在导入时自动实例化,你可以编写一个模块,在该模块中直接创建并导出一个已实例化的对象。
以下是一个简单的示例代码,演示了如何实现这一点:
javascript
// fetchAct.js
class FetchAct {
constructor() {
// 可以在这里添加一些默认配置
}
get(url, config) {
// 实现 GET 请求逻辑
}
post(url, data, config) {
// 实现 POST 请求逻辑
}
// 其他 HTTP 请求方法...
// 你可以添加其他自定义方法...
}
// 创建并导出一个已实例化的 FetchAct 对象
export default new FetchAct();
在这个示例中,我们定义了一个名为 FetchAct
的类,它包含了各种 HTTP 请求方法(例如 get
、post
等)。然后,我们使用 new FetchAct()
创建了一个实例,并将其作为默认导出,这样其他模块就可以直接导入并使用这个已实例化的对象了:
javascript
// 使用 fetchAct.js 中导出的已实例化对象
import fetchAct from "./fetchAct";
fetchAct
.get("/users")
.then((response) => {
console.log(response.data);
})
.catch((error) => {
console.error("Error:", error);
});
通过这种方式,你就可以在导入时直接使用 fetchAct
对象,而不需要在每个模块中都创建一个新的实例。